蘋果新的程式語言 Swift 語言進階(十二)--選項鍊

goohong發表於2014-06-19

            選項鍊是使用選項來查詢和呼叫其屬性、方法或下標的一個過程,如果選項包含一個值,則屬性、方法、下標的查詢和呼叫成功,否則,呼叫返回nil。

         選項鍊能用在任何型別的選項來檢查對其一個屬性、方法、下標的查詢和呼叫是否成功。

         選項鍊可以作為強制展開的替代方式使用,但選項鍊的使用更加安全,不會觸發一個執行時錯誤。

         在呼叫一個選項的屬性、方法或下標方法時,通過在該選項值的後面放置一個(?)標記來規定一個選項鍊。這與在選項值後放置一個(!) 來強制展開選項的值非常相似。主要的不同是在選項值為nil時選項鍊能夠得體的失敗,不會觸發一個執行時錯誤。

         選項鍊與Objective-C語言中的發訊息給nil類似,選項鍊能允許在一個nil值上進行屬性、方法、下標的呼叫和查詢。為了反應這個事實,   選項鍊的呼叫結果總是返回一個選項值,即使你查詢的屬性、方法、下標返回一個非選項值的情況。然後可以使用這個返回值來檢查選項鍊的呼叫是否成功。

         尤其是選項鍊的返回結果除了被封裝為一個選項外與返回值的型別相同。如一個正常返回一個Int的屬性當使用 選項鍊來存取時返回一個整形選項(Int?)。

          下面例子展示了選項鍊的使用:

  classPerson {

   var residence:Residence?

}

 

class Residence {

 var rooms =Room[]()

   var numberOfRooms:Int {

   return rooms.count

    }

   subscript(i:Int) ->Room {

       return rooms[i]

    }

         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 buildingName {

           return buildingName

        }else if buildingNumber {

           return buildingNumber

        }else {

           return nil

        }

    }

}


            let john =Person()

 if let roomCount =john.residence?.numberOfRooms {

   println("John's residence has\(roomCount) room(s).")

 }else {

   println("Unable to retrieve the number of rooms.")

}

        以上例子中john例項的屬性residence是一個選項,在沒有為john例項的屬性residence賦值時,執行else分支,如果john例項的屬性residence已經賦值,則執行if 分支。而無論哪種情況,程式碼都不會出現執行時錯誤。


                多個選項鍊能連結到一起,如果鏈上的任何連結返回nil,則整個鏈失敗。這允許檢查和呼叫一個選項屬性的子屬性包含的屬性、方法、下標方法以及更深的呼叫。如下例子展示了多個選項鍊如何連結到一起。 

           if let johnsStreet = john.residence?.address?.street {

      println("John's street name is\(johnsStreet).")

     }else {

      println("Unable to retrieve the address.")

    }

       下例展示如何通過選項鍊呼叫下標方法:

if let firstRoomName =john.residence?[0].name {

   println("The first room name is\(firstRoomName).")

}else {

   println("Unable to retrieve the first room name.")

}

              下例展示如何通過選項鍊呼叫一個例項方法。

if let buildingIdentifier =john.residence?.address?.buildingIdentifier() {

   println("John's building identifier is\(buildingIdentifier).")

}

       由於Address例項方法buildingIdentifier返回的也是一個選項,因此還可以進一步連結。如下所示:

     if let upper = john.residence?.address?.buildingIdentifier()?.uppercaseString {

       println("John's uppercase building identifier is\(upper).")

     }

        


相關文章