UIKit에서 Build를 기다리는 도중,
아래와 같은 오류코드가 발생한 후, 실행이 안되는 경우를 종종 경험하실 수 있습니다!
Terminating app due to uncaught exception 'NSUnknownKeyException', reason: ...
terminating with uncaught exception of type NSException
(lldb)
코드 상으로는 완벽한것 같은데, 위와 같은 런타임에러가 발생하는 이유는 무엇일까요?
이유는 즉,
IBOutlet 혹은 IBAction와 같은 컴포넌트(Componets)의 값이 비어있기(nil) 때문입니다!
Components는 Optional 타입
@IBOutlet 뒤에 붙은 ! 키워드
아래 View에 위치한 Hello는 Label 컴포넌트이며,
ViewController 내 연결을 통해 @IBOutlet hello 변수가 생성된 상태입니다.
@IBOutlet 변수(코드)는, Hello란 컴포넌트와 연결이 되는 동시에,
'특정 값'이 반드시 존재한다는 전제하에 강제 언래핑(Forced Unwrapped) 된 코드로 작성됩니다.
@IBOutlet weak var hello: UILabel!
즉, hello라는 생성된 라벨은 View 상에서 반드시 존재하며,
그렇기 때문에 코드상으로는 UILabel 옵셔널 타입이 아닌, 강제 언래핑을 나타내주는 방식입니다.
컴포넌트(View) - 코드(ViewController) 간 연결
위와 같은 작업을 완료하게 되면,
ViewController의 Inspector 내 'Outlet' 탭에서
Hello(컴포넌트) - Hello(@IBOutlet) 연결 현황을 확인할 수 있습니다.
오류 발생
1. 코드상의 변수명을 변경한 후, 업데이트(연결) 하지 않았을 경우
만약, ViewController 코드에 선언된 IBOutlets의 명칭을 아래와 같이 'bye'로 변경한다면?
- 기존의 hello라는 변수는 nil값이 되므로, 런타임 오류가 발생합니다!
2. 코드상의 변수를 삭제(주석) 할 경우
또한, 코드에 선언된 IBOutlets를 사용하지 않아 삭제, 혹은 주석처리를 할 경우
위 경우와 동일하게 오류가 발생합니다!
오류 해결방법
결과적으로, '연결'에 대한 관심이 반드시 필요합니다.
(Connections Inspector에도 변경사항을 반영해야 합니다)
- 변수명을 변경하게 될 경우 ➟ 기존 연결을 해제하고, 새롭게 연결을 진행
- 변수를 삭제 혹은 주석처리 할 경우 ➟ 더 이상 사용하지 않는다면 연결을 해제
댓글