옵셔널은 swift 에서 가장 핵심적인 개념중 하나이다.
func someFunction(someOptionalParam: Int?) {
// ....
}
someFunction(someOptionalParam: nil) // 오류이 잘 작동
위와 같은 someFunction
같은 경우는 Int?
를 통해 옵셔널이라고 말한다.
즉 nil 값이 올 수 있다는 뜻이다. 따라서 매개변수로 nil를 넣어도 문제 없이 잘 작동한다.
func someFunction(someOptionalParam: Int) {
// ....
}
someFunction(someParam: nil) // 오류발생
그러나 위 코드는 Int
라고 정확히 명시하면서 nil값이 포함되지 않는다는 뜻을 포함하고 있어서
함수의 매개변수로 nil 값을 넣을시에 오류가 발생한다.
옵셔널을 사용하면서 nil값의 가능성을 코드만으로도 표현이 가능하다.
따라서 nil 의 가능성을 문서화하지 않아도 되니까 문서나 주석을 작성하는 시간을 절약할 수 있다.
전달값이 옵셔널이 아니라면 nil 값을 체크하지 않아도 되기 때문에 효율적으로 코드를 작성할 수 있다.
또한 예외 사항을 최소화 할 수 있는 안전한 코딩이 가능하다.
옵셔널은 사실 enum(열거형)과 generics의 합작품이라고 볼 수 있다. (뒤에 다시 배울것이다.)
옵셔널 선언은 다음과 같이 할 수 있다.
enum Optional<Wrapped>: ExpressibleByNiliteral {
case none
case some(Wrapped)
}
열거형이 기본 타입이다.
위 코드와 같이 옵셔널 타입이 none
즉, 없다와 some(Wrapped)
즉, 있다 두가지 case로 구성 되어있다.
let optionalValue: Optional<Int> = nil
let optionalValue: Int? =nil
옵셔널을 선언할 때 타입은 위 코드 맨 윗줄과 같이 표현해야 하는게 완전한 문법이지만
그 밑에줄 같이 Int?
로 표현해 Int
가 옵셔널 타입이다 라는 것을 말해준다.
이때 물음표는 반드시 붙어있어야 한다.
옵셔널을 표현할 때 물음표와 느낌표 두가지를 사용한다.
먼저 느낌표를 확인해보자
var implicitlyUnwrappedOptionalValue: Int! = 100
switch implicitlyUnwrappedOptionalValue {
case .none:
print("This Optional variable is nil")
case .some(let value):
print("Value is \(value)")
}
앞서 보았듯이 case가 값이 있는 경우와 없는 경우로 나뉜다.
// 기존 변수처럼 사용 가능
OptionalValue = OptionalValue + 1
// nil 할당 가능
OptionalValue = nil
암시적 추출 옵셔널은 기존의 변수처럼 사용할 수 있다.
암시적 추출 옵셔널은 변수를 깬다음에 그 안에 정수값 123을 가져오기 때문에 연산을 해도 문제가 발생하지 않지만 기본적인 옵셔널은 옵셔널 값을 그대로(박스안에 있는 상태로) 가져오기 때문에 연산시 서로 다른 타입이기 때문에 오류가 발생한다
// 잘못된 접근으로 인한 런타임 오류 발생
OptionalValue = OptionalValue + 1
그러나 앞서 OptionalValue
값에 nil 를 넣고 위 코드 처럼 + 1 을 하기 위해 OptionalValue
를 불러오면 런타임 오류가 발생한다.
이제 물음표를 사용하는 경우를 보자 물음표를 사용하는 것은 일반적인 옵셔널이다.
var optionalValue: Int? = 100
switch optionalValue {
case .none:
print("This Optional variable is nil")
case .some(let value):
print("Value is \(value)")
}
앞서 암시적 추출 옵셔널과 크게 다를바가 없고 Int
뒤에 물음표가 온다는 차이점이 있다.
// nil 할당 가능
optionalValue = nil
// 기존 변수처럼 사용불가 - 옵셔널과 일반 값은 다른 타입이므로 연산불가
//optionalValue = optionalValue + 1
하지만 물음표를 사용하는 옵셔널은 nil 값은 할당이 가능하지만 기존의 변수처럼 사용은 불가하다.
이유는 옵셔널과 일반 값은 서로 다른 타입으로 보기 때문에 연산이 불가능하다.