你可以將多層可選鏈連接在一起,可以掘取模型內更下層的屬性方法和子腳本。然而多層可選鏈不能再添加比已經返回的可選值更多的層。 也就是說:
如果你試圖獲得的類型不是可選類型,由于使用了可選鏈它將變成可選類型。 如果你試圖獲得的類型已經是可選類型,由于可選鏈它也不會提高可選性。
因此:
如果你試圖通過可選鏈獲得Int值,不論使用了多少層鏈接返回的總是Int?。 相似的,如果你試圖通過可選鏈獲得Int?值,不論使用了多少層鏈接返回的總是Int?。
下面的例子試圖獲取john的residence屬性里的address的street屬性。這里使用了兩層可選鏈來聯(lián)系residence和address屬性,它們兩者都是可選類型:
if let johnsStreet = john.residence?.address?.street {
println("John's street name is \(johnsStreet).")
} else {
println("Unable to retrieve the address.")
}
// 打印 "Unable to retrieve the address.”。
john.residence的值現(xiàn)在包含一個Residence實例,然而john.residence.address現(xiàn)在是nil,因此john.residence?.address?.street調用失敗。
從上面的例子發(fā)現(xiàn),你試圖獲得street屬性值。這個屬性的類型是String?。因此盡管在可選類型屬性前使用了兩層可選鏈,john.residence?.address?.street的返回值類型也是String?。
如果你為Address設定一個實例來作為john.residence.address的值,并為address的street屬性設定一個實際值,你可以通過多層可選鏈來得到這個屬性值。
let johnsAddress = Address()
johnsAddress.buildingName = "The Larches"
johnsAddress.street = "Laurel Street"
john.residence!.address = johnsAddress
if let johnsStreet = john.residence?.address?.street {
println("John's street name is \(johnsStreet).")
} else {
println("Unable to retrieve the address.")
}
// 打印 "John's street name is Laurel Street."。
值得注意的是,“!”符號在給john.residence.address分配address實例時的使用。john.residence屬性是一個可選類型,因此你需要在它獲取address屬性之前使用!解析以獲得它的實際值。