Swift中應用可選類型完善處理占位成績。本站提示廣大學習愛好者:(Swift中應用可選類型完善處理占位成績)文章只能為提供參考,不一定能成為您想要的結果。以下是Swift中應用可選類型完善處理占位成績正文
可選類型是Swift中新引入的,功效很壯大。在這篇博文裡評論辯論的,是在Swift裡,若何經由過程可選類型來包管強類型的平安性。作為例子,我們來創立一個Objective-C API的Swift版本,但現實上Swift自己其實不須要如許的API。
為Dictionary增長objectsForKeys函數
在Objective-C中,NSDictionary有一個辦法-objectsForKeys:NoFoundMarker:, 這個辦法須要一個NSArray數組作為鍵值參數,然後前往一個包括相干值的數組。文檔裡寫到:"前往數組中的第N個值,和輸出數組中的第N個值絕對應",那假如有某個鍵值在字典裡不存在呢?因而就有了notFoundMarker作為前往提醒。好比第三個鍵值沒有找到,那末在前往數組中第三個值就是這個notFoundMarker,而不是字典中的第三個值,然則這個值只是用來提示原字典中沒有找到對應值,但在前往數組中該元素存在,且用notFoundMarker作為占位符,由於這個對象不克不及直接應用,所以在Foundation框架中有個專門的類處置這個情形:NSNull。
在Swift中,Dictionary類沒有相似objectsForKeys的函數,為了解釋成績,我們著手加一個,而且使其成為操作字典值的通用辦法。我們可以用extension來完成:
extension Dictionary{
func valuesForKeys(keys:[K], notFoundMarker: V )->[V]{
//詳細完成代碼前面會寫到
}
}
以上就是我們完成的Swift版本,這個和Objective-C版本有很年夜差別。在Swift中,由於其強類型的緣由限制了前往的成果數組只能包括單一類型的元素,所以我們不克不及放NSNull在字符串數組中,然則,Swift有更好的選擇,我們可以前往一個可選類型數據。我們一切的值都封包在可選類型中,而不是NSNull, 我們只用nil便可以了。
extension Dictionary{
func valuesForKeys(keys: [Key]) -> [Value?] {
var result = [Value?]()
result.reserveCapacity(keys.count)
for key in keys{
result.append(self[key])
}
return result
}
}
Swift中更輕便的辦法
小同伴們能夠會問,為何Swift中不須要完成這麼一個API呢?其實其有更簡略的完成,以下面代碼所示:
extension Dictionary {
func valuesForKeys(keys: [Key]) -> [Value?] {
return keys.map { self[$0] }
}
}
上述方法完成的功效和最開端的辦法完成的功效雷同,固然焦點的功效是封裝了map的挪用,這個例子也解釋了為何Swift沒有供給輕量級的API接口,由於小同伴們簡略的挪用map便可以完成。
接上去,我們試驗幾個例子:
var dic: Dictionary = [ "1": 2, "3":3, "4":5 ]
var t = dic.valuesForKeys(["1", "4"])
//成果為:[Optional(2), Optional(5)]
var t = dict.valuesForKeys(["3", "9"])
// 成果為:[Optional(3), nil]
t = dic.valuesForKeys([])
//成果為:[]
內嵌可選類型
如今,假如我們為每個成果挪用last辦法,看下成果若何?
var dic: Dictionary = [ "1": 2, "3":3, "4":5 ]
var t = dic.valuesForKeys(["1", "4"]).last //成果為:Optional(Optional(5))
// Optional(Optional("Ching"))
var t = dict.valuesForKeys(["3", "9"]).last
// 成果為:Optional(nil)
var t = dict.valuesForKeys([]).last
// 成果為:nil
小同伴們立馬含混了,為何會湧現兩層包括的可選類型呢?,特殊對第二種情形的Optional(nil),這是甚麼節拍?
我們回過火看看last屬性的界說:
var last:T? { get }
很顯著last屬性的類型是數組元素類型的可選類型,這類情形下,由於元素類型是(String?),那末再聯合前往的類型,因而其成果就是String??了,這就是所謂的嵌套可選類型。但嵌套可選類型實質是甚麼意思呢?
假如在Objective-C中從新挪用上述辦法,我們將應用NSNull作為占位符,Objective-C的挪用語法以下所示:
[dict valuesForKeys:@[@"1", @"4"] notFoundMarker:[NSNull null]].lastObject
// 5
[dict valuesForKeys:@[@"1", @"3"] notFoundMarker:[NSNull null]].lastObject
// NSNull
[dict valuesForKeys:@[] notFoundMarker:[NSNull null]].lastObject
// nil
不論是Swift版本照樣Objective-C版本,前往值為nil都意味數組是空的,所以它就沒有最初一個元素。 然則假如前往是Optional(nil)或許Objective-C中的NSNull都表現數組中的最初一個元素存在,然則元素的內容是空的。在Objective-C中只能借助NSNull作為占位符來到達這個目標,然則Swift卻可以說話體系類型的角度的完成。
供給一個默許值
進一步封裝,假如我字典中的某個或某些元素不存在,我們想供給一個默許值怎樣辦呢?完成辦法很簡略:
extension Dictionary {
func valuesForKeys( keys:[Key], notFoundMarker: Value)->[Value]{
return self.valueForKeys(kes).map{ $0 ?? notFoundMarker }
}
}
dict.valuesForKeys(["1", "5"], notFoundMarker: "Anonymous")
和Objective-C比擬,其須要占位符來到達占位的目標,然則Swift卻曾經從說話類型體系的層面原生的支撐了這類用法,同時供給了豐碩的語法功效。這就是Swift可選類型的壯大的地方。同時留意上述例子頂用到了空合運算符??。