Swift 可选链
可选链的定义:可选链是可以请求和调用属性、方法和子脚本的过程,
用于请求或调用的目标可能为nil
可选链可能会返回两个值:
1.目标有值,就会调用成功,返回对应值
2.目标为nil,调用返回nil
多次请求或调用可以被链接成一个链,如果任意一个节点为nil将导致整条链失效
可选链可替代强制解析
通过在属性、方法、下标脚本的可选值后面放一个问号(?),来定义一个可选链
可选链(?) | 感叹号(!)强制展开方法,属性,下标脚本可选链 |
---|---|
?放置于可选值后面,来调用方法、属性、下标脚本 | !放置于可选值后面来调用方法、属性、下标脚本来强制展开值 |
当可选为nil输出比较友好的错误信息 | 当可选为nil时强制展开执行错误 |
使用(!)可选链
class Person {
var residence:Residence?
}
class Residence {
var numberOfRooms = 1
}
调用
func optionalChainingFunc(){
let john = Person()
//将导致运行时错误
#2022-03-11 10:07:42.377595+0800 Swift_study[1957:63338] Swift_study/OptionalChainingStudy.swift:35: Fatal error: Unexpectedly found nil while unwrapping an Optional value
let roomCount = john.residence!.numberOfRooms
}
调用结果
//导致运行时错误
2022-03-11 10:07:42.377595+0800 Swift_study[1957:63338] Swift_study/OptionalChainingStudy.swift:35: Fatal error: Unexpectedly found nil while unwrapping an Optional value
使用(?)可选链
func optionalChainingFunc(){
let john = Person()
if let roomInfo = john.residence?.numberOfRooms{
print("John 的房间号为 \(roomInfo)。")
}else {
print("不能查看房间号")
}
}
调用结果
不能查看房间号
为可选链定义模型类
可以使用可选链多层调用属性、方法、和下标脚本。使得可以利用它们之间的复杂模型来获取更底层的属性,并能够检查是否可以成功获取此类底层属性。
例
定义了四个模型类,包含多层可选链
// Room 定义一个name属性和一个设定room名的初始化器
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 buildingName != nil {
return buildingName
}else if buildingNumber != nil {
return buildingNumber
}else {
return nil
}
}
}
//住宅类
class Residence{
// 定义了一个变量 rooms,它被初始化为一个Room[]类型的空数组
var rooms = [Room]()
var numberOfRooms:Int{
return rooms.count
}
//定义下标脚本
subscript (i:Int) -> Room {
return rooms[i]
}
func printNumberOfRooms(){
print("房间号\(numberOfRooms)")
}
//声明地址可选链
var address:Address?
}
class Person{
//声明地址可选链
var residence:Residence?
}
通过可选链调用方法(对返回可选值的函数进行链接)
let john = Person()
//通过可选链调用可选值的方法并检查方法调用是否成功
if john.residence?.printNumberOfRooms() != nil{
print("有房间号输出")
}else {
print("无法输出房间号")
}
调用结果
无法输出房间号
通过可选链调用下标脚本
使用可选链尝试从下标脚本获取值并检查下标脚本的调用是否成功,但是不能通过可选链来设置下标脚本
let john = Person()
//使用可选链调用下标脚本
// john.residence 是可选链试图获得的可选值
if let firstRoomName = john.residence?[0].name{
print("第一个房间名 \(firstRoomName).")
}else {
print("无法查找到房间")
}
调用结果
无法查找到房间
有值调用(成功调用)
let john = Person()
let johnsHouse = Residence()
//用下标来对可选值进行读取或写入
johnsHouse.rooms.append(Room(name: "厨房"))
johnsHouse.rooms.append(Room(name: "客厅"))
john.residence = johnsHouse
//通过可选链接调用来访问下标
if let firstRoomName = john.residence?[0].name {
print("John 的第一个房间为:\(firstRoomName)")
} else {
print("无法查找到房间")
}
let johnsAddress = Address()
johnsAddress.buildingName = "幸福大厦"
johnsAddress.street = "幸福路"
john.residence!.address = johnsAddress
//使用了两层可选链来联系residence和address属性
if let johnsStreet = john.residence?.address?.street{
print("John 所在的街道是 \(johnsStreet)。")
}else {
print("无法检索到地址。 ")
}
调用结果
John 的第一个房间为:厨房
John 所在的街道是 幸福路。
连接多层链接
可以将多层可选链接连接在一起,可以掘取模型内更下层的属性方法和下标脚本,但是多层可选链不能再添加比已经返回的可选值更多的层
例:如果试图通过可选链获得Int值,不论使用了多少层链接返回的总是Int?。 相似的,如果试图通过可选链获得Int?值,不论使用了多少层链接返回的总是Int?。
网友评论