100 days of swiftui: 14
https://www.hackingwithswift.com/100/swiftui/14
값을 지닐 수도 있고 안 지닐 수도 있는 타입이다. 예로 아래 sentence
는 String 값을 지닐 수도 있고 값이 없는 nil
일 수도 있다.
let sentence: String?
nil
은 ""
, []
, 0
처럼 초기화된 값이나 빈 String, 배열, 0이 아니다. 그래서 optional을 의미하는 String?
과 String
은 다르다. 그러므로 optinal은 non-optional 값처럼 사용할 수 없고, unwrap 과정을 거쳐 non-optional로 변경한 후 사용할 수 있다.
예:
var number: Int? = nil
number = 30
//if number > 10 {
// print("\(number) is bigger than 10. (1)")
//}
if let number = number {
if number > 10 {
print("\(number) is bigger than 10. (2)")
}
} else {
print("number is unwrapped.")
}
//if number > 10 {
// print("\(number) is bigger than 10. (3)")
//}
주석 처리한 코드는 swift가 안정성을 위해 실행하지 않는다.
if let
을 통해 unwrap할 수 있다.if let
을 사용할 때 일반적으로 같은 이름의 상수에 unwrap한다.코드 파일
https://github.com/soaringwave/Ios-studying/commit/568d625600847b581ae98e95ebabd779874a21e0
if let
말고도 guard
도 unwrap할 때 사용할 수 있다.
func checkStringHasValue(textInput: String?) {
guard let textInput = textInput else {
print("There is no text.")
return
}
print("'\(textInput)' is input.")
}
checkStringHasValue(textInput: nil)
checkStringHasValue(textInput: "")
결과:
There is no text.
'' is input.
위 예시에서 알 수 있듯이 guard
는if let
과 달리 아래 두 특징이 있다.
dictionary의 default처럼, 값이 없는 경우를 대비해 미리 값을 지정할 수도 있다. [optional의 데이터] ?? [optional의 데이터가 nil일 경우 대체할 값]
을 입력하면 된다.
예:
struct Computer {
var user: String?
var model: String
}
var computer1 = Computer(user: "user1", model: "macbook pro 1")
var computer2 = Computer(user: nil, model: "macbook pro 2")
let user2 = computer2.user ?? "unknown"
print(user2)
결과:
unknown
❗️ nil coalescing도 같은 타입으로 설정해야 한다. 아래 예시는 String?과 Int를 사용해서 안된다.
let tempString: String? = "example"
let tempExample = tempString ?? 0
코드 파일
https://github.com/soaringwave/Ios-studying/commit/3aac475a5503fabc0de2d5149aa80b2029083b77
// 1
let credentials = ["twostraws", "fr0sties"]
let lowercaseUsername = credentials.first.lowercased()
// 2
let songs: [String]? = [String]()
let finalSong = songs.last.count
// 3
let capitals = ["Scotland": "Edinburgh", "Wales": "Cardiff"]
let scottishCapital = capitals["Scotland"].uppercased()
위 코드는 모두 swift에서 에러가 나는 코드다.
credentials
이 빈 배열이라서 credentials.first
가 없을 수도 있는데 lowercased()
를 사용한다. songs
가 nil
일 수도 있고 마찬가지로 songs.last
가 존재하지 않을 수도 있는데 count
를 사용한다.capitals["Scotland"]
가 존재하지 않을 수 있는데 uppercased()
를 사용한다.이 코드처럼 존재하지 않는 값을 참조할 때를 대비해서, '값이 존재한다면 뒤를 실행해줘'인 optional changing ?
를 사용하면 된다.
// 1
let credentials = ["twostraws", "fr0sties"]
let lowercaseUsername = credentials.first?.lowercased()
// 2
let songs: [String]? = [String]()
let finalSong = songs?.last?.count
// 3
let capitals = ["Scotland": "Edinburgh", "Wales": "Cardiff"]
let scottishCapital = capitals["Scotland"]?.uppercased()
struct Book {
var title: String
var author: String?
}
let book1: Book? = nil
let authorOfBook1 = book1?.author?.first?.uppercased() ?? "U"
print(authorOfBook1)
코드 파일
https://github.com/soaringwave/Ios-studying/commit/1f4d338fb71639c1e8273adfb663832502fca7e3
throw
와 try?
를 활용해서 에러를 관리할 수 있다고 이해했다. 지금 당장 코드를 직관적으로 이해하기도 어렵고 동작원리도 이해하기 어려워서 다시 공부해야겠다.
https://www.hackingwithswift.com/quick-start/beginners/how-to-handle-function-failure-with-optionals