這里的教程為Swift官方教程中文版。

語(yǔ)句(Statements)


1.0 翻譯:coverxit 校對(duì):numbbbbb, coverxit, stanzhai

2.0 翻譯+校對(duì):littledogboy

2.2 翻譯:chenmingbiao

3.0 翻譯:chenmingjia

本頁(yè)包含內(nèi)容:

在 Swift 中,有三種類(lèi)型的語(yǔ)句:簡(jiǎn)單語(yǔ)句、編譯器控制語(yǔ)句和控制流語(yǔ)句。簡(jiǎn)單語(yǔ)句是最常見(jiàn)的,用于構(gòu)造表達(dá)式或者聲明。編譯器控制語(yǔ)句允許程序改變編譯器的行為,包含編譯配置語(yǔ)句和行控制語(yǔ)句。

控制流語(yǔ)句則用于控制程序執(zhí)行的流程,Swift 中有多種類(lèi)型的控制流語(yǔ)句:循環(huán)語(yǔ)句、分支語(yǔ)句和控制轉(zhuǎn)移語(yǔ)句。循環(huán)語(yǔ)句用于重復(fù)執(zhí)行代碼塊;分支語(yǔ)句用于執(zhí)行滿足特定條件的代碼塊;控制轉(zhuǎn)移語(yǔ)句則用于改變代碼的執(zhí)行順序。另外,Swift 提供了 do 語(yǔ)句,用于構(gòu)建局部作用域,還用于錯(cuò)誤的捕獲和處理;還提供了 defer 語(yǔ)句,用于退出當(dāng)前作用域之前執(zhí)行清理操作。

是否將分號(hào)(;)添加到語(yǔ)句的末尾是可選的。但若要在同一行內(nèi)寫(xiě)多條獨(dú)立語(yǔ)句,則必須使用分號(hào)。

語(yǔ)句語(yǔ)法
</a> 語(yǔ)句表達(dá)式 ;可選
語(yǔ)句聲明 ;可選
語(yǔ)句循環(huán)語(yǔ)句 ;可選
語(yǔ)句分支語(yǔ)句 ;可選
語(yǔ)句帶標(biāo)簽的語(yǔ)句 ;可選
語(yǔ)句控制轉(zhuǎn)移語(yǔ)句 ;可選
語(yǔ)句defer 語(yǔ)句 ;可選
語(yǔ)句do 語(yǔ)句 :可選
語(yǔ)句編譯器控制語(yǔ)句
多條語(yǔ)句語(yǔ)句 多條語(yǔ)句可選

循環(huán)語(yǔ)句

循環(huán)語(yǔ)句會(huì)根據(jù)特定的循環(huán)條件來(lái)重復(fù)執(zhí)行代碼塊。Swift 提供三種類(lèi)型的循環(huán)語(yǔ)句:for-in 語(yǔ)句、while 語(yǔ)句和 repeat-while 語(yǔ)句。

通過(guò) break 語(yǔ)句和 continue 語(yǔ)句可以改變循環(huán)語(yǔ)句的控制流。有關(guān)這兩條語(yǔ)句,詳情參見(jiàn) Break 語(yǔ)句Continue 語(yǔ)句。

循環(huán)語(yǔ)句語(yǔ)法
循環(huán)語(yǔ)句for-in 語(yǔ)句
循環(huán)語(yǔ)句while 語(yǔ)句
循環(huán)語(yǔ)句repeat-while 語(yǔ)句

For-In 語(yǔ)句

for-in 語(yǔ)句會(huì)為集合(或?qū)崿F(xiàn)了 SequenceType 協(xié)議的任意類(lèi)型)中的每一項(xiàng)執(zhí)行一次代碼塊。

for-in 語(yǔ)句的形式如下:

for 項(xiàng) in 集合 {  
    循環(huán)體語(yǔ)句  
}

for-in 語(yǔ)句在循環(huán)開(kāi)始前會(huì)調(diào)用集合表達(dá)式的 generate() 方法來(lái)獲取一個(gè)實(shí)現(xiàn)了 GeneratorType 協(xié)議的類(lèi)型的值。接下來(lái)循環(huán)開(kāi)始,反復(fù)調(diào)用該值的 next() 方法。如果其返回值不是 None,它將會(huì)被賦給“項(xiàng)”,然后執(zhí)行循環(huán)體語(yǔ)句,執(zhí)行完畢后回到循環(huán)開(kāi)始處,繼續(xù)重復(fù)這一過(guò)程;否則,既不會(huì)賦值也不會(huì)執(zhí)行循環(huán)體語(yǔ)句,for-in 語(yǔ)句至此執(zhí)行完畢。

for-in 語(yǔ)句語(yǔ)法
for-in 語(yǔ)句for case可選 模式 in 表達(dá)式 where子句可選 代碼塊

While 語(yǔ)句

只要循環(huán)條件為真,while 語(yǔ)句就會(huì)重復(fù)執(zhí)行代碼塊。

while 語(yǔ)句的形式如下:

while 條件 {  
    語(yǔ)句 
}

while 語(yǔ)句的執(zhí)行流程如下:

  1. 判斷條件的值。如果為 true,轉(zhuǎn)到第 2 步;如果為 falsewhile 語(yǔ)句至此執(zhí)行完畢。
  2. 執(zhí)行循環(huán)體中的語(yǔ)句,然后重復(fù)第 1 步。

由于會(huì)在執(zhí)行循環(huán)體中的語(yǔ)句前判斷條件的值,因此循環(huán)體中的語(yǔ)句可能會(huì)被執(zhí)行若干次,也可能一次也不會(huì)被執(zhí)行。

條件的結(jié)果必須是Bool類(lèi)型或者Bool的橋接類(lèi)型。另外,條件語(yǔ)句也可以使用可選綁定,請(qǐng)參閱 可選綁定。

while 語(yǔ)句語(yǔ)法

while 語(yǔ)句while 條件子句 代碼塊

條件子句表達(dá)式
條件子句表達(dá)式 , 條件列表
條件子句條件列表
條件子句可用性條件 , 表達(dá)式

條件列表條件 | 條件 , 條件列表
</a> 條件表達(dá)式 |可用性條件 | case條件 | 可選綁定條件
case 條件case 模式 構(gòu)造器

可選綁定條件let 模式 構(gòu)造器 | var 模式 構(gòu)造器

Repeat-While 語(yǔ)句

repeat-while 語(yǔ)句至少執(zhí)行一次代碼塊,之后只要循環(huán)條件為真,就會(huì)重復(fù)執(zhí)行代碼塊。

repeat-while 語(yǔ)句的形式如下:

repeat {  
    語(yǔ)句  
} while 條件

repeat-while 語(yǔ)句的執(zhí)行流程如下:

  1. 執(zhí)行循環(huán)體中的語(yǔ)句,然后轉(zhuǎn)到第 2 步。
  2. 判斷條件的值。如果為 true,重復(fù)第 1 步;如果為 false,repeat-while 語(yǔ)句至此執(zhí)行完畢。

由于條件的值是在循環(huán)體中的語(yǔ)句執(zhí)行后才進(jìn)行判斷,因此循環(huán)體中的語(yǔ)句至少會(huì)被執(zhí)行一次。

條件的結(jié)果必須是Bool類(lèi)型或者Bool的橋接類(lèi)型。另外,條件語(yǔ)句也可以使用可選綁定,請(qǐng)參閱 可選綁定。

repeat-while 語(yǔ)句語(yǔ)法
repeat-while 語(yǔ)句repeat 代碼塊 while 表達(dá)式

分支語(yǔ)句

分支語(yǔ)句會(huì)根據(jù)一個(gè)或者多個(gè)條件來(lái)執(zhí)行指定部分的代碼。分支語(yǔ)句中的條件將會(huì)決定程序如何分支以及執(zhí)行哪部分代碼。Swift 提供兩種類(lèi)型的分支語(yǔ)句:if 語(yǔ)句和 switch 語(yǔ)句。

if 語(yǔ)句和 switch 語(yǔ)句中的控制流可以用 break 語(yǔ)句改變,請(qǐng)參閱 Break 語(yǔ)句

分支語(yǔ)句語(yǔ)法
分支語(yǔ)句if 語(yǔ)句
分支語(yǔ)句guard 語(yǔ)句
分支語(yǔ)句switch 語(yǔ)句

If 語(yǔ)句

if 語(yǔ)句會(huì)根據(jù)一個(gè)或多個(gè)條件來(lái)決定執(zhí)行哪一塊代碼。

if 語(yǔ)句有兩種基本形式,無(wú)論哪種形式,都必須有花括號(hào)。

第一種形式是當(dāng)且僅當(dāng)條件為真時(shí)執(zhí)行代碼,像下面這樣:

if 條件 {  
    語(yǔ)句  
}

第二種形式是在第一種形式的基礎(chǔ)上添加 else 語(yǔ)句,當(dāng)只有一個(gè) else 語(yǔ)句時(shí),像下面這樣:

if 條件 {    
    若條件為真則執(zhí)行這部分語(yǔ)句    
} else {           
    若條件為假則執(zhí)行這部分語(yǔ)句
}

else 語(yǔ)句也可包含 if 語(yǔ)句,從而形成一條鏈來(lái)測(cè)試更多的條件,像下面這樣:

if 條件1 {  
    若條件1為真則執(zhí)行這部分語(yǔ)句  
} else if 條件2 {  
    若條件2為真則執(zhí)行這部分語(yǔ)句
} else {  
    若前兩個(gè)條件均為假則執(zhí)行這部分語(yǔ)句
}

if 語(yǔ)句中條件的結(jié)果必須是Bool類(lèi)型或者Bool的橋接類(lèi)型。另外,條件語(yǔ)句也可以使用可選綁定,請(qǐng)參閱 可選綁定。

if 語(yǔ)句語(yǔ)法
</a> if 語(yǔ)句if 條件子句 代碼塊 else子句可選
else 子句else 代碼塊 | else if語(yǔ)句

Guard 語(yǔ)句

如果一個(gè)或者多個(gè)條件不成立,可用 guard 語(yǔ)句用來(lái)退出當(dāng)前作用域。

guard 語(yǔ)句的格式如下:

guard 條件 else {    
    語(yǔ)句    
}

guard 語(yǔ)句中條件的結(jié)果必須是Bool類(lèi)型或者Bool的橋接類(lèi)型。另外,條件也可以是一條可選綁定,請(qǐng)參閱 可選綁定。

guard 語(yǔ)句中進(jìn)行可選綁定的常量或者變量,其可用范圍從聲明開(kāi)始直到作用域結(jié)束。

guard 語(yǔ)句必須有 else 子句,而且必須在該子句中調(diào)用 Never 返回類(lèi)型的函數(shù),或者使用下面的語(yǔ)句退出當(dāng)前作用域:

  • return
  • break
  • continue
  • throw

關(guān)于控制轉(zhuǎn)移語(yǔ)句,請(qǐng)參閱 控制轉(zhuǎn)移語(yǔ)句。關(guān)于Never返回類(lèi)型的函數(shù),請(qǐng)參閱 永不返回的函數(shù)。

guard 語(yǔ)句語(yǔ)法
guard 語(yǔ)句guard 條件子句 else 代碼塊

Switch 語(yǔ)句

switch 語(yǔ)句會(huì)根據(jù)控制表達(dá)式的值來(lái)決定執(zhí)行哪部分代碼。

switch 語(yǔ)句的形式如下:

switch 控制表達(dá)式 {  
case 模式1:  
    語(yǔ)句  
case 模式2 where 條件:  
    語(yǔ)句  
case 模式3 where 條件, 模式4 where 條件:  
    語(yǔ)句
default:  
    語(yǔ)句
}

switch 語(yǔ)句會(huì)先計(jì)算控制表達(dá)式的值,然后與每一個(gè) case 的模式進(jìn)行匹配。如果匹配成功,程序?qū)?huì)執(zhí)行對(duì)應(yīng)的 case 中的語(yǔ)句。另外,每一個(gè) case 都不能為空,也就是說(shuō)在每一個(gè) case 中必須至少有一條語(yǔ)句。如果你不想在匹配到的 case 中執(zhí)行代碼,只需在該 case 中寫(xiě)一條 break 語(yǔ)句即可。

可以用作控制表達(dá)式的值是十分靈活的。除了標(biāo)量類(lèi)型外,如 Int、Character,你可以使用任何類(lèi)型的值,包括浮點(diǎn)數(shù)、字符串、元組、自定義類(lèi)型的實(shí)例和可選類(lèi)型??刂票磉_(dá)式的值還可以用來(lái)匹配枚舉類(lèi)型中的成員值或是檢查該值是否包含在指定的 Range 中。關(guān)于如何在 switch 語(yǔ)句中使用這些類(lèi)型,請(qǐng)參閱 控制流 一章中的 Switch。

每個(gè) case 的模式后面可以有一個(gè) where 子句。where 子句由 where 關(guān)鍵字緊跟一個(gè)提供額外條件的表達(dá)式組成。因此,當(dāng)且僅當(dāng)控制表達(dá)式匹配一個(gè) case 的模式且 where 子句的表達(dá)式為真時(shí),case 中的語(yǔ)句才會(huì)被執(zhí)行。在下面的例子中,控制表達(dá)式只會(huì)匹配包含兩個(gè)相等元素的元組,例如 (1, 1)

case let (x, y) where x == y:

正如上面這個(gè)例子,也可以在模式中使用 let(或 var)語(yǔ)句來(lái)綁定常量(或變量)。這些常量(或變量)可以在對(duì)應(yīng)的 where 子句以及 case 中的代碼中使用。但是,如果一個(gè) case 中含有多個(gè)模式,所有的模式必須包含相同的常量(或變量)綁定,并且每一個(gè)綁定的常量(或變量)必須在所有的條件模式中都有相同的類(lèi)型。

switch 語(yǔ)句也可以包含默認(rèn)分支,使用 default 關(guān)鍵字表示。只有所有 case 都無(wú)法匹配控制表達(dá)式時(shí),默認(rèn)分支中的代碼才會(huì)被執(zhí)行。一個(gè) switch 語(yǔ)句只能有一個(gè)默認(rèn)分支,而且必須在 switch 語(yǔ)句的最后面。

switch 語(yǔ)句中 case 的匹配順序和源代碼中的書(shū)寫(xiě)順序保持一致。因此,當(dāng)多個(gè)模式都能匹配控制表達(dá)式時(shí),只有第一個(gè)匹配的 case 中的代碼會(huì)被執(zhí)行。

Switch 語(yǔ)句不能有遺漏

在 Swift 中,switch 語(yǔ)句中控制表達(dá)式的每一個(gè)可能的值都必須至少有一個(gè) case 與之對(duì)應(yīng)。在某些無(wú)法面面俱到的情況下(例如,表達(dá)式的類(lèi)型是 Int),你可以使用 default 分支滿足該要求。

不存在隱式落入

當(dāng)匹配到的 case 中的代碼執(zhí)行完畢后,switch 語(yǔ)句會(huì)直接退出,而不會(huì)繼續(xù)執(zhí)行下一個(gè) case 。這就意味著,如果你想執(zhí)行下一個(gè) case,需要顯式地在當(dāng)前 case 中使用 fallthrough 語(yǔ)句。關(guān)于 fallthrough 語(yǔ)句的更多信息,請(qǐng)參閱 Fallthrough 語(yǔ)句。

switch 語(yǔ)句語(yǔ)法

switch 語(yǔ)句switch 表達(dá)式 { switch-case列表可選 }
</a> switch case 列表switch-case switch-case列表可選
switch casecase標(biāo)簽 多條語(yǔ)句 | default標(biāo)簽 多條語(yǔ)句

case 標(biāo)簽case case項(xiàng)列表 :
</a> case 項(xiàng)列表模式 where子句可選 | 模式 where子句可選 , case項(xiàng)列表
default 標(biāo)簽default :

where-clausewhere where表達(dá)式
where-expression表達(dá)式

帶標(biāo)簽的語(yǔ)句

你可以在循環(huán)語(yǔ)句或 switch 語(yǔ)句前面加上標(biāo)簽,它由標(biāo)簽名和緊隨其后的冒號(hào)(:)組成。在 breakcontinue 后面跟上標(biāo)簽名可以顯式地在循環(huán)語(yǔ)句或 switch 語(yǔ)句中改變相應(yīng)的控制流。關(guān)于這兩條語(yǔ)句用法,請(qǐng)參閱 Break 語(yǔ)句Continue 語(yǔ)句

標(biāo)簽的作用域在該標(biāo)簽所標(biāo)記的語(yǔ)句內(nèi)。可以嵌套使用帶標(biāo)簽的語(yǔ)句,但標(biāo)簽名必須唯一。

關(guān)于使用帶標(biāo)簽的語(yǔ)句的例子,請(qǐng)參閱 控制流 一章中的 帶標(biāo)簽的語(yǔ)句

帶標(biāo)簽的語(yǔ)句語(yǔ)法
</a> 帶標(biāo)簽的語(yǔ)句語(yǔ)句標(biāo)簽 循環(huán)語(yǔ)句 | 語(yǔ)句標(biāo)簽 if語(yǔ)句 | 語(yǔ)句標(biāo)簽 switch語(yǔ)句
語(yǔ)句標(biāo)簽標(biāo)簽名稱(chēng) :
標(biāo)簽名稱(chēng)標(biāo)識(shí)符

控制轉(zhuǎn)移語(yǔ)句

控制轉(zhuǎn)移語(yǔ)句能夠無(wú)條件地把控制權(quán)從一片代碼轉(zhuǎn)移到另一片代碼,從而改變代碼執(zhí)行的順序。Swift 提供五種類(lèi)型的控制轉(zhuǎn)移語(yǔ)句:break 語(yǔ)句、continue 語(yǔ)句、fallthrough 語(yǔ)句、return 語(yǔ)句和 throw 語(yǔ)句。

控制轉(zhuǎn)移語(yǔ)句語(yǔ)法
控制轉(zhuǎn)移語(yǔ)句break 語(yǔ)句
控制轉(zhuǎn)移語(yǔ)句continue 語(yǔ)句
控制轉(zhuǎn)移語(yǔ)句fallthrough 語(yǔ)句
控制轉(zhuǎn)移語(yǔ)句return 語(yǔ)句
控制轉(zhuǎn)移語(yǔ)句throw 語(yǔ)句

Break 語(yǔ)句

break 語(yǔ)句用于終止循環(huán)語(yǔ)句、if 語(yǔ)句或 switch 語(yǔ)句的執(zhí)行。使用 break 語(yǔ)句時(shí),可以只寫(xiě) break 這個(gè)關(guān)鍵詞,也可以在 break 后面跟上標(biāo)簽名,像下面這樣:

break
break 標(biāo)簽名

當(dāng) break 語(yǔ)句后面帶標(biāo)簽名時(shí),可用于終止由這個(gè)標(biāo)簽標(biāo)記的循環(huán)語(yǔ)句、if 語(yǔ)句或 switch 語(yǔ)句的執(zhí)行。

而只寫(xiě) break 時(shí),則會(huì)終止 switch 語(yǔ)句或 break 語(yǔ)句所屬的最內(nèi)層循環(huán)語(yǔ)句的執(zhí)行。不能使用 break 語(yǔ)句來(lái)終止未使用標(biāo)簽的 if 語(yǔ)句。

無(wú)論哪種情況,控制權(quán)都會(huì)被轉(zhuǎn)移給被終止的控制流語(yǔ)句后面的第一行語(yǔ)句。

關(guān)于使用 break 語(yǔ)句的例子,請(qǐng)參閱 控制流 一章的 Break帶標(biāo)簽的語(yǔ)句。

break 語(yǔ)句語(yǔ)法
break 語(yǔ)句break 標(biāo)簽名稱(chēng)可選

Continue 語(yǔ)句

continue 語(yǔ)句用于終止循環(huán)中當(dāng)前迭代的執(zhí)行,但不會(huì)終止該循環(huán)的執(zhí)行。使用 continue 語(yǔ)句時(shí),可以只寫(xiě) continue 這個(gè)關(guān)鍵詞,也可以在 continue 后面跟上標(biāo)簽名,像下面這樣:

continue
continue 標(biāo)簽名

當(dāng) continue 語(yǔ)句后面帶標(biāo)簽名時(shí),可用于終止由這個(gè)標(biāo)簽標(biāo)記的循環(huán)中當(dāng)前迭代的執(zhí)行。

而當(dāng)只寫(xiě) continue 時(shí),可用于終止 continue 語(yǔ)句所屬的最內(nèi)層循環(huán)中當(dāng)前迭代的執(zhí)行。

在這兩種情況下,控制權(quán)都會(huì)被轉(zhuǎn)移給循環(huán)語(yǔ)句的條件語(yǔ)句。

for 語(yǔ)句中,continue 語(yǔ)句執(zhí)行后,增量表達(dá)式還是會(huì)被計(jì)算,這是因?yàn)槊看窝h(huán)體執(zhí)行完畢后,增量表達(dá)式都會(huì)被計(jì)算。

關(guān)于使用 continue 語(yǔ)句的例子,請(qǐng)參閱 控制流 一章的 Continue帶標(biāo)簽的語(yǔ)句

continue 語(yǔ)句語(yǔ)法
continue 語(yǔ)句continue 標(biāo)簽名稱(chēng)可選

Fallthrough 語(yǔ)句

fallthrough 語(yǔ)句用于在 switch 語(yǔ)句中轉(zhuǎn)移控制權(quán)。fallthrough 語(yǔ)句會(huì)把控制權(quán)從 switch 語(yǔ)句中的一個(gè) case 轉(zhuǎn)移到下一個(gè) case。這種控制權(quán)轉(zhuǎn)移是無(wú)條件的,即使下一個(gè) case 的模式與 switch 語(yǔ)句的控制表達(dá)式的值不匹配。

fallthrough 語(yǔ)句可出現(xiàn)在 switch 語(yǔ)句中的任意 case 中,但不能出現(xiàn)在最后一個(gè) case 中。同時(shí),fallthrough 語(yǔ)句也不能把控制權(quán)轉(zhuǎn)移到使用了值綁定的 case。

關(guān)于在 switch 語(yǔ)句中使用 fallthrough 語(yǔ)句的例子,請(qǐng)參閱 控制流 一章的 控制轉(zhuǎn)移語(yǔ)句。

fallthrough 語(yǔ)句語(yǔ)法
fallthrough 語(yǔ)句fallthrough

Return 語(yǔ)句

return 語(yǔ)句用于在函數(shù)或方法的實(shí)現(xiàn)中將控制權(quán)轉(zhuǎn)移到調(diào)用函數(shù)或方法,接著程序?qū)?huì)從調(diào)用位置繼續(xù)向下執(zhí)行。

使用 return 語(yǔ)句時(shí),可以只寫(xiě) return 這個(gè)關(guān)鍵詞,也可以在 return 后面跟上表達(dá)式,像下面這樣:

return
return 表達(dá)式

當(dāng) return 語(yǔ)句后面帶表達(dá)式時(shí),表達(dá)式的值將會(huì)返回給調(diào)用函數(shù)或方法。如果表達(dá)式的值的類(lèi)型與函數(shù)或者方法聲明的返回類(lèi)型不匹配,Swift 則會(huì)在返回表達(dá)式的值之前將表達(dá)式的值的類(lèi)型轉(zhuǎn)換為返回類(lèi)型。

注意
正如 可失敗構(gòu)造器 中所描述的,return nil 在可失敗構(gòu)造器中用于表明構(gòu)造失敗。

而只寫(xiě) return 時(shí),僅僅是從該函數(shù)或方法中返回,而不返回任何值(也就是說(shuō),函數(shù)或方法的返回類(lèi)型為 Void 或者說(shuō) ())。

return 語(yǔ)句語(yǔ)法
return 語(yǔ)句return 表達(dá)式可選

Throw 語(yǔ)句

throw 語(yǔ)句出現(xiàn)在拋出函數(shù)或者拋出方法體內(nèi),或者類(lèi)型被 throws 關(guān)鍵字標(biāo)記的閉包表達(dá)式體內(nèi)。

throw 語(yǔ)句使程序在當(dāng)前作用域結(jié)束執(zhí)行,并向外圍作用域傳播錯(cuò)誤。拋出的錯(cuò)誤會(huì)一直傳遞,直到被 do 語(yǔ)句的 catch 子句處理掉。

throw 語(yǔ)句由 throw 關(guān)鍵字緊跟一個(gè)表達(dá)式組成,如下所示:

throw 表達(dá)式

表達(dá)式的結(jié)果必須符合 ErrorType 協(xié)議。

關(guān)于如何使用 throw 語(yǔ)句的例子,請(qǐng)參閱 錯(cuò)誤處理 一章的 用 throwing 函數(shù)傳遞錯(cuò)誤。

throw 語(yǔ)句語(yǔ)法
throw 語(yǔ)句throw 表達(dá)式

Defer 語(yǔ)句

defer 語(yǔ)句用于在退出當(dāng)前作用域之前執(zhí)行代碼。

defer 語(yǔ)句形式如下:

defer {
    語(yǔ)句
}

defer 語(yǔ)句中的語(yǔ)句無(wú)論程序控制如何轉(zhuǎn)移都會(huì)被執(zhí)行。在某些情況下,例如,手動(dòng)管理資源時(shí),比如關(guān)閉文件描述符,或者即使拋出了錯(cuò)誤也需要執(zhí)行一些操作時(shí),就可以使用 defer 語(yǔ)句。

如果多個(gè) defer 語(yǔ)句出現(xiàn)在同一作用域內(nèi),那么它們執(zhí)行的順序與出現(xiàn)的順序相反。給定作用域中的第一個(gè) defer 語(yǔ)句,會(huì)在最后執(zhí)行,這意味著代碼中最靠后的 defer 語(yǔ)句中引用的資源可以被其他 defer 語(yǔ)句清理掉。

func f() {
    defer { print("First") }
    defer { print("Second") }
    defer { print("Third") }
}
f()
// 打印 “Third”
// 打印 “Second”
// 打印 “First”

defer 語(yǔ)句中的語(yǔ)句無(wú)法將控制權(quán)轉(zhuǎn)移到 defer 語(yǔ)句外部。

defer 語(yǔ)句語(yǔ)法
延遲語(yǔ)句defer 代碼塊

Do 語(yǔ)句

do 語(yǔ)句用于引入一個(gè)新的作用域,該作用域中可以含有一個(gè)或多個(gè) catch 子句,catch 子句中定義了一些匹配錯(cuò)誤條件的模式。do 語(yǔ)句作用域內(nèi)定義的常量和變量只能在 do 語(yǔ)句作用域內(nèi)使用。

Swift 中的 do 語(yǔ)句與 C 中限定代碼塊界限的大括號(hào)({})很相似,也并不會(huì)降低程序運(yùn)行時(shí)的性能。

do 語(yǔ)句的形式如下:

do {
    try 表達(dá)式
    語(yǔ)句
} catch 模式1 {
    語(yǔ)句
} catch 模式2 where 條件 {
    語(yǔ)句
}

如同 switch 語(yǔ)句,編譯器會(huì)判斷 catch 子句是否有遺漏。如果 catch 子句沒(méi)有遺漏,則認(rèn)為錯(cuò)誤已被處理。否則,錯(cuò)誤會(huì)自動(dòng)傳遞到外圍作用域,被某個(gè) catch 子句處理掉或者被用 throws 關(guān)鍵字聲明的拋出函數(shù)繼續(xù)向外拋出。

為了確保錯(cuò)誤已經(jīng)被處理,可以讓 catch 子句使用匹配所有錯(cuò)誤的模式,如通配符模式(_)。如果一個(gè) catch 子句不指定一種具體模式,catch 子句會(huì)匹配任何錯(cuò)誤,并綁定到名為 error 的局部常量。有關(guān)在 catch 子句中使用模式的更多信息,請(qǐng)參閱 模式。

關(guān)于如何在 do 語(yǔ)句中使用一系列 catch 子句的例子,請(qǐng)參閱 錯(cuò)誤處理

do 語(yǔ)句語(yǔ)法
</a> do 語(yǔ)句do 代碼塊 多條 catch子句可選
多條 catch 子句catch子句 多條 catch子句可選
catch 子句catch 模式可選 where子句可選 代碼塊

編譯器控制語(yǔ)句

編譯器控制語(yǔ)句允許程序改變編譯器的行為。Swift 有兩種編譯器控制語(yǔ)句:編譯配置語(yǔ)句和線路控制語(yǔ)句。

編譯器控制語(yǔ)句語(yǔ)法
編譯器控制語(yǔ)句編譯配置語(yǔ)句
編譯器控制語(yǔ)句線路控制語(yǔ)句

編譯配置語(yǔ)句

編譯配置語(yǔ)句可以根據(jù)一個(gè)或多個(gè)配置來(lái)有條件地編譯代碼。

每一個(gè)編譯配置語(yǔ)句都以 #if 開(kāi)始,#endif 結(jié)束。如下是一個(gè)簡(jiǎn)單的編譯配置語(yǔ)句:

#if 編譯配置項(xiàng)
    語(yǔ)句
#endif

if 語(yǔ)句的條件不同,編譯配置的條件是在編譯時(shí)進(jìn)行判斷的。只有編譯配置在編譯時(shí)判斷為 true 的情況下,相應(yīng)的語(yǔ)句才會(huì)被編譯和執(zhí)行。

編譯配置可以是 truefalse 的字面量,也可以是使用 -D 命令行標(biāo)志的標(biāo)識(shí)符,或者是下列表格中的任意一個(gè)平臺(tái)檢測(cè)函數(shù)。

函數(shù) 可用參數(shù)
os() OSX, iOS, watchOS, tvOS, Linux
arch() i386, x86_64, arm, arm64
swift() >= 后跟版本號(hào)

swift()(語(yǔ)言版本檢測(cè)函數(shù))的版本號(hào)參數(shù)主要由主版本號(hào)和次版本號(hào)組成并且使用點(diǎn)號(hào)(.)分隔開(kāi),>= 和版本號(hào)之間不能有空格。

注意
arch(arm) 平臺(tái)檢測(cè)函數(shù)在 ARM 64 位設(shè)備上不會(huì)返回 true。如果代碼在 32 位的 iOS 模擬器上編譯,arch(i386) 平臺(tái)檢測(cè)函數(shù)會(huì)返回 true

你可以使用邏輯操作符 &&、||! 來(lái)組合多個(gè)編譯配置,還可以使用圓括號(hào)來(lái)進(jìn)行分組。

就像 if 語(yǔ)句一樣,你可以使用 #elseif 子句來(lái)添加任意多個(gè)條件分支來(lái)測(cè)試不同的編譯配置。你也可以使用 #else 子句來(lái)添加最終的條件分支。包含多個(gè)分支的編譯配置語(yǔ)句例子如下:

#if 編譯配置1
    如果編譯配置1成立則執(zhí)行這部分代碼
#elseif 編譯配置2
    如果編譯配置2成立則執(zhí)行這部分代碼
#else
    如果編譯配置均不成立則執(zhí)行這部分代碼
#endif

注意
即使沒(méi)有被編譯,編譯配置中的語(yǔ)句仍然會(huì)被解析。然而,唯一的例外是編譯配置語(yǔ)句中包含語(yǔ)言版本檢測(cè)函數(shù):僅當(dāng) Swift 編譯器版本和語(yǔ)言版本檢測(cè)函數(shù)中指定的版本號(hào)匹配時(shí),語(yǔ)句才會(huì)被解析。這種設(shè)定能確保舊的編譯器不會(huì)嘗試去解析新 Swift 版本的語(yǔ)法。

編譯配置語(yǔ)句語(yǔ)法

單個(gè)編譯配置語(yǔ)句#if 編譯配置 語(yǔ)句可選 多個(gè)編譯配置elseif子句可選 - 單個(gè)編譯配置else子句可選 #endif
</a> 多個(gè)編譯配置 elseif 子句單個(gè)編譯配置elseif子句 多個(gè)編譯配置elseif子句可選
單個(gè)編譯配置 elseif 子句#elseif 編譯配置 語(yǔ)句可選
單個(gè)編譯配置 else 子句#else 語(yǔ)句可選

編譯配置平臺(tái)檢測(cè)函數(shù)
編譯配置語(yǔ)言版本檢測(cè)函數(shù)
編譯配置標(biāo)識(shí)符
編譯配置布爾值字面量
編譯配置( 編譯配置 )
編譯配置! 編譯配置
編譯配置編譯配置 && 編譯配置
編譯配置編譯配置 || 編譯配置

平臺(tái)檢測(cè)函數(shù)os ( 操作系統(tǒng) )
平臺(tái)檢測(cè)函數(shù)arch ( 架構(gòu) )
</a> 語(yǔ)言版本檢測(cè)函數(shù)swift ( >= swift版本 )
操作系統(tǒng)OSX | iOS | watchOS | tvOS
</a> 架構(gòu)i386 | x86_64 | arm | arm64
swift 版本十進(jìn)制數(shù)字 -. -十進(jìn)制數(shù)字

行控制語(yǔ)句

行控制語(yǔ)句可以為被編譯的源代碼指定行號(hào)和文件名,從而改變?cè)创a的定位信息,以便進(jìn)行分析和調(diào)試。

行控制語(yǔ)句形式如下:

#sourceLocation(file: 文件名 , line:行號(hào))

#sourceLocation()

第一種的行控制語(yǔ)句會(huì)改變?cè)撜Z(yǔ)句之后的代碼中的字面量表達(dá)式 #line#file 所表示的值。行號(hào) 是一個(gè)大于 0 的整形字面量,會(huì)改變 #line 表達(dá)式的值。文件名 是一個(gè)字符串字面量,會(huì)改變 #file 表達(dá)式的值。

第二種的行控制語(yǔ)句, #sourceLocation(),會(huì)將源代碼的定位信息重置回默認(rèn)的行號(hào)和文件名。

行控制語(yǔ)句語(yǔ)法

行控制語(yǔ)句#sourceLocation(file:文件名,line:行號(hào))
行控制語(yǔ)句#sourceLocation()
</a> 行號(hào) → 大于 0 的十進(jìn)制整數(shù)
文件名靜態(tài)字符串字面量

可用性條件

可用性條件可作為 ifwhileguard 語(yǔ)句的條件,可以在運(yùn)行時(shí)基于特定的平臺(tái)參數(shù)來(lái)查詢(xún) API 的可用性。

可用性條件的形式如下:

if #available(平臺(tái)名稱(chēng) 版本, ..., *) {    
    如果 API 可用,則執(zhí)行這部分語(yǔ)句    
} else {    
    如果 API 不可用,則執(zhí)行這部分語(yǔ)句
}

使用可用性條件來(lái)執(zhí)行一個(gè)代碼塊時(shí),取決于使用的 API 在運(yùn)行時(shí)是否可用,編譯器會(huì)根據(jù)可用性條件提供的信息來(lái)決定是否執(zhí)行相應(yīng)的代碼塊。

可用性條件使用一系列逗號(hào)分隔的平臺(tái)名稱(chēng)和版本。使用 iOS,OSX,以及 watchOS 等作為平臺(tái)名稱(chēng),并寫(xiě)上相應(yīng)的版本號(hào)。* 參數(shù)是必須寫(xiě)的,用于處理未來(lái)的潛在平臺(tái)??捎眯詶l件確保了運(yùn)行時(shí)的平臺(tái)不低于條件中指定的平臺(tái)版本時(shí)才執(zhí)行代碼塊。

與布爾類(lèi)型的條件不同,不能用邏輯運(yùn)算符 &&|| 組合可用性條件。

可用性條件語(yǔ)法

可用性條件#available ( 可用性參數(shù)列表 )
</a> 可用性參數(shù)列表可用性參數(shù) | 可用性參數(shù) , 可用性參數(shù)列表
可用性參數(shù)平臺(tái)名稱(chēng) 平臺(tái)版本
可用性條件*

平臺(tái)名稱(chēng)iOS | iOSApplicationExtension
平臺(tái)名稱(chēng)OSX | OSXApplicationExtension
平臺(tái)名稱(chēng)watchOS
平臺(tái)版本十進(jìn)制數(shù)字
平臺(tái)版本十進(jìn)制數(shù)字 . 十進(jìn)制數(shù)字
平臺(tái)版本十進(jìn)制數(shù)字 . 十進(jìn)制數(shù)字 . 十進(jìn)制數(shù)字

? 表達(dá)式 聲明 ?
?