Swift 3.0 版本將會(huì)去掉沿用已經(jīng)的 C 風(fēng)格循環(huán)語法, 又是向現(xiàn)代開發(fā)語言的一次邁進(jìn), 咱們就來看看沒了 C 風(fēng)格循環(huán)我們還有什么選擇, 看過之后你會(huì)不會(huì)感覺 C 風(fēng)格循環(huán)在 Swift 中確實(shí)有點(diǎn)多余呢?
關(guān)于 C 風(fēng)格循環(huán), 不我們過多介紹了, 就是類似這樣的語句:
let numberList = [1, 2, 3, 4, 5] for var i = 0; i < numberList.count; i++ { }
如今這樣的語法在新版本的 Swift 中即將成為歷史了, C 風(fēng)格的循環(huán)語法可能是大家最熟悉的, 大家會(huì)不會(huì)覺得突然去掉這個(gè)語法有些不適應(yīng)呢? 咱們再來看看 Swift 3 中的替代方案。
第一個(gè)替代方案, 我們可以使用 for .. in 這樣的語法:
let numberList = [1, 2, 3, 4, 5] var result = "" for num in numberList { result += "\(num) " }這樣就完成了對數(shù)組的遍歷了, 但是還有另一個(gè)情況, 如果我們想知道每次遍歷的索引怎么辦呢, 還有一種方法:
for num in numberList.enumerate() { result += "[\(num.index)]\(num.element) " }
我們可以使用這個(gè)集合類型的 enumerate 方法,將這個(gè)數(shù)組的索引和對應(yīng)的元素都取了出來,然后我們在循環(huán)中就可以對索引項(xiàng)進(jìn)行引用了, num.index 和 num.element 分別代表對應(yīng)的索引和元素。
上面這個(gè)循環(huán)我們還可以再改寫一下:
for (index, item) in numberList.enumerate() { result += "[\(index)]\(item) " }
不難看出,其實(shí)循環(huán)中的每一項(xiàng)都是一個(gè)元組(Tuple),這個(gè)元組的第一項(xiàng)是當(dāng)前的索引, 第二項(xiàng)是當(dāng)前的數(shù)組元素。 那么我們就可以推理出, enumerate 函數(shù)其實(shí)就是對 numberList 數(shù)組做了一個(gè)變換,原來它是一個(gè) Int 類型的數(shù)組,經(jīng)過變換后,成為了 (Int, Int) 元組類型的數(shù)組。
是不是這么回事呢? 查看 enumerate 方法的文檔后, 看到它的定義是這樣的:
func enumerate() -> EnumerateSequence<Array<Element>>比我們想象的要復(fù)雜些, EnumerateSequence 是個(gè)什么鬼, 讓我們再來看看它的文檔定義:
The SequenceType returned by enumerate(). EnumerateSequence is a sequence of pairs (n, x), where ns are consecutive Ints starting at zero, and xs are the elements of a Base SequenceType
仔細(xì)看下, 其實(shí)跟我們理解的還是差不多的, 它只不過是對集合類的一個(gè)集成, 這個(gè)集合每一項(xiàng)是一個(gè)元組 (n, x) , n 代表索引, x 代表數(shù)組元素。
那么,我們還可以做點(diǎn)更有意思的事情:
for (index, item) in numberList.enumerate().reverse() { result += "[\(index)]\(item) " }調(diào)用 enumerate, 之后再調(diào)用 reverse 方法, 我們就可以對一個(gè)數(shù)組進(jìn)行反向遍歷。
for (index, item) in numberList.enumerate().reverse() { result += "[\(index)]\(item) " }我們還可以:
for (index, item) in numberList.enumerate().filter({ (index, item) in index % 2 == 0}) { result += "[\(index)]\(item) " }
調(diào)用 filter 函數(shù),過濾某些索引, 只遍歷符合條件的那些元素。
當(dāng)然, 我們還可以做的更多更多, 大家有興趣可以看看 SequenceType 的文檔,把你的新思路回復(fù)給大家。http://swiftdoc.org/v2.2/protocol/SequenceType
除了剛才咱們說的這些, Swift 還提供了更方便的循環(huán)語法, 叫做 Range 循環(huán)。 比如這樣:
var rs = ""; for i in 0...10 { rs += "\(i)" } print(rs)這個(gè)語句會(huì)輸出 0 到 10 之間的所有數(shù)字, 0…10 這個(gè)表示 Range 區(qū)間的范圍。 當(dāng)然,對于我們剛才的數(shù)組遍歷來說, 一般數(shù)組索引都是數(shù)組長度減去 1, 用這個(gè)區(qū)間處理起來就會(huì)比較麻煩, 不過好在 Swift 給我們提供了另外一種 Range 方法:
for i in 0..<numberList.count { rs += "\(i)" }
這次我們換成了 0..<numberList.count, 這種形式會(huì)排除閉區(qū)間最后那個(gè)數(shù)組,然后我們就可以在循環(huán)中用索引進(jìn)行訪問啦(注意符號 ..< 兩邊不要有空格)。
好了,今天跟大家分享的內(nèi)容就這么多。C 風(fēng)格的循環(huán)語句其實(shí)更多是我們的一個(gè)長期養(yǎng)成的習(xí)慣問題。 世界的一切都在進(jìn)步發(fā)展,包括開發(fā)語言也是一樣。 看了 Swift 提供的循環(huán)語法, 你對 C 風(fēng)格循環(huán)還有沒有存在的必要時(shí)什么看法呢。 早些擁抱趨勢和變化總是好的。