override func viewDidLoad() {
super.viewDidLoad()
//可选链
//可选链是访问或调用可选类型的属性, 方法, 下标的过程, 如果可选类型有值则调用成功, 否则返回 nil.
//多个访问可以链接在一起, 其中一个访问失败,则整个链表失败.
//1. 可选链作为另一种强制解包的方式
//表达形式: 在可选值后加 "?"
//可选链和强制解包的区别: 可选链值为 nil 失败, 但是不会引起崩溃.
//可选链的返回值总是为可选类型, 即使调用属性, 方法, 下标的返回值为非可选类型, 返回值类型是相应的可选类型
class Person {
var residence: Residence?
var name: String?
}
class Residence {
var numberOfRooms = 1
}
let john = Person()
//直接强制解包会报错
// let roomCount = john.residence!.numberOfRooms
//使用可选链, 在可选值后加 "?"
let roomCount = john.residence?.numberOfRooms
//residence 没有初始化, 默认为 nil
if let roomNum = john.residence?.numberOfRooms {
print("John's residence has \(roomNum) room(s).")
} else {
print("Unable to retrieve the number of rooms.")
}
// Prints "Unable to retrieve the number of rooms."
//给 john.residence 赋一个实例对象, 它的值不再为 nil
john.residence = Residence()
//numberOfRooms 为非可选 Int 型, 但是在可选链中仍然返回可选类型
if let roomNum1 = john.residence?.numberOfRooms {
print("John's residence has \(roomNum1) room(s).")
} else {
print("Unable to retrieve the number of rooms.")
}
// Prints "John's residence has 1 room(s)."
//2. 为可选链定义 Model 类
//可以使用可选链, 访问复杂 Model的多个层级的属性, 方法, 下标
class PersonClass {
var residence: ResidenceClass?
}
class ResidenceClass {
var rooms = [Room]()
var numberOfRooms: Int {
return rooms.count
}
subscript(i: Int) -> Room {
get {
return rooms[i]
}
set {
rooms[i] = newValue
}
}
func printNumberOfRooms() {
print("The number of room is \(numberOfRooms)")
}
var address: Address?
}
class Room {
let name: String
init(name: String) { self.name = name }
}
class Address {
var buildingName: String?
var buildingNumber: String?
var street: String?
func buildingIdentifier() -> String? {
if let buildingNumber = buildingNumber, let street = street {
return "\(buildingNumber) \(street)"
} else if buildingName != nil {
return buildingName
} else {
return nil
}
}
}
//3. 通过可选链访问属性
//通过可选链获取属性
let johnSon = PersonClass()
if let roomCount = johnSon.residence?.numberOfRooms {
print("John's residence has \(roomCount) room(s).")
} else {
print("Unable to retrieve the number of rooms.")
}
// Prints "Unable to retrieve the number of rooms."
//通过可选链设置属性
//因为 john.residence 为 nil 赋值失败, 等号右边没有被调用
func createAddress() -> Address {
print("Function was called.")
let someAddress = Address()
someAddress.buildingNumber = "29"
someAddress.street = "Acacia Road"
return someAddress
}
johnSon.residence?.address = createAddress()
//4. 通过可选链调用方法
//可以用可选链调用一个函数,并检查是否调用成功,即使函数没有返回值
// func printNumberOfRooms() {
// print("The number of rooms is \(numberOfRooms)")
// }
//用可选链调用函数时, 返回值是可选类型(void 会变为 void?) , 可以使用if 语句判断是否可以调用printNumberOfRooms() 方法
if johnSon.residence?.printNumberOfRooms() != nil {
print("It was possible to print the number of rooms.")
} else {
print("It was not possible to print the number of rooms.")
}
// Prints "It was not possible to print the number of rooms."
// if (johnSon.residence?.address = someAddress) != nil {
// print("It was possible to set the address.")
// } else {
// print("It was not possible to set the address.")
// }
// Prints "It was not possible to set the address."
//5. 通过可选链获取下标
//可以使用可选链获取设置一个可选值的下标, 并检查下标调用是否成功
//用可选链获取下标, ? 放在括号前
if let firstRoomName = johnSon.residence?[0].name {
print("The first room name is \(firstRoomName).")
} else {
print("Unable to retrieve the first room name.")
}
// Prints "Unable to retrieve the first room name."
//6. 获取可选类型的下标
//如果一个下标返回可选类型的值就像字典那样, 在闭括号后加 ?
var testScores = ["Dave": [86, 82, 84], "Bev": [79, 94, 81]]
testScores["Dave"]?[0] = 91
testScores["Bev"]?[0] += 1
testScores["Brian"]?[0] = 72
// the "Dave" array is now [91, 82, 84] and the "Bev" array is now [80, 94, 81]
//7. 连接多个层级的可选链
//用可选链获取一个值, 如果这个值是非可选的, 返回值会变为可选
if let johnsStreet = johnSon.residence?.address?.street {
print("John's street name is \(johnsStreet).")
} else {
print("Unable to retrieve the address.")
}
// Prints "Unable to retrieve the address."
//john.residence.address 为 nil 调用失败
let johnsAddress = Address()
johnsAddress.buildingName = "The Larches"
johnsAddress.street = "Laurel Street"
johnSon.residence?.address = johnsAddress
if let johnsStreet = johnSon.residence?.address?.street {
print("John's street name is \(johnsStreet).")
} else {
print("Unable to retrieve the address.")
}
// Prints "John's street name is Laurel Street."
//8. 返回值为可选类型的 chain
//可选链的调用函数的返回值也是可选类型
if let buildingIdentifier = johnSon.residence?.address?.buildingIdentifier() {
print("John's building identifier is \(buildingIdentifier).")
}
// Prints "John's building identifier is The Larches."
//如果想进一步对返回值使用可选链, 可以在方法的双括号后添加 ?
if let beginsWithThe =
johnSon.residence?.address?.buildingIdentifier()?.hasPrefix("The") {
if beginsWithThe {
print("John's building identifier begins with \"The\".")
} else {
print("John's building identifier does not begin with \"The\".")
}
}
// Prints "John's building identifier begins with "The"."
}Swift- 可选链
最新推荐文章于 2025-09-10 08:26:54 发布
本文主要介绍了Swift中可选链的相关知识。可选链是访问或调用可选类型属性、方法、下标的过程,若可选类型有值则调用成功,否则返回nil。文中通过多个示例,详细阐述了可选链作为强制解包方式、访问属性、调用方法、获取下标等方面的应用。

2958

被折叠的 条评论
为什么被折叠?



