switch

switch

switch語句最簡單的形式就是把某個值與一個或若干個相同類型的值作比較:

switch 'some value to consider' { 
case 'value 1': 
    'respond to value 1' 
case 'value 2', 
'value 3': 
    'respond to value 2 or 3' 
default: 
    'otherwise, do something else' 
} 

下面的例子使用switch語句來匹配一個名為someCharacter的小寫字符:

let someCharacter: Character = "e" 
switch someCharacter { 
case "a", "e", "i", "o", "u": 
    println("\(someCharacter) is a vowel") 
case "b", "c", "d", "f", "g", "h", "j", "k", "l", "m", 
"n", "p", "q", "r", "s", "t", "v", "w", "x", "y", "z": 
    println("\(someCharacter) is a consonant") 
default: println("\(someCharacter) is not a vowel or a consonant") 
} 
// prints "e is a vowel" 

在 Swift 中流纹,當匹配的case塊中的代碼執(zhí)行完畢后,程序會終止switch語句,而不會繼續(xù)執(zhí)行下一個case塊。這也就是說,不需要在case塊中顯式地使用break語句。這使得switch語句更安全、更易用摊唇,也避免了因忘記寫break語句而產(chǎn)生的錯誤。

每一個case塊都必須包含至少一條語句涯鲁。像下面這樣書寫代碼是無效的巷查,因為第一個case塊是空的:

let anotherCharacter: Character = "a" 
switch anotherCharacter { 
case "a": 
case "A": 
    println("The letter A") 
default: 
    println("Not the letter A") 
} 
// this will report a compile-time error 

不像C語言里的switch語句有序,在 Swift 中,switch語句不會同時匹配"a"和"A"岛请。相反的旭寿,上面的代碼會引起編譯期錯誤:case "a": does not contain any executable statements——這就避免了意外地從一個case塊貫穿到另外一個,使得代碼更安全崇败、也更直觀盅称。

一個case也可以包含多個模式,用逗號把它們分開(如果太長了也可以分行寫):

switch `some value to consider` { 
case `value 1`, 
`value 2`: 
    `statements` 
} 

注意:如果想要貫穿特定的case塊中后室,請使用fallthrough語句

Fallthrough

如果你確實需要C風(fēng)格的落入(fallthrough)的特性缩膝,你可以在每個需要該特性的case分支中使用fallthrough關(guān)鍵字。下面的例子使用fallthrough來創(chuàng)建一個數(shù)字的描述語句岸霹。

let integerToDescribe = 5 
var description = "The number \(integerToDescribe) is" 
switch integerToDescribe { 
case 2, 3, 5, 7, 11, 13, 17, 19: 
    description += " a prime number, and also" 
    fallthrough 
default: 
    description += " an integer." 
} 
println(description) 
// prints "The number 5 is a prime number, and also an integer." 

NOTE:fallthrough關(guān)鍵字不會檢查它下一個將會落入執(zhí)行的case中的匹配條件疾层。fallthrough簡單地使代碼執(zhí)行繼續(xù)連接到下一個case中的執(zhí)行代碼,這和C語言標準中的switch語句特性是一樣的贡避。

范圍匹配

case塊的模式也可以是一個值的范圍云芦。下面的例子展示了如何使用范圍匹配來輸出任意數(shù)字對應(yīng)的自然語言格式:

let count = 3_000_000_000_000 
let countedThings = "stars in the Milky Way" 
var naturalCount: String 
switch count { 
case 0: 
    naturalCount = "no" 
case 1...3: 
    naturalCount = "a few" 
case 4...9: 
    naturalCount = "several" 
case 10...99: 
    naturalCount = "tens of" 
case 100...999: naturalCount = "hundreds of" 
case 1000...999_999: naturalCount = "thousands of" 
default: 
    naturalCount = "millions and millions of" 
} 
println("There are \(naturalCount) \(countedThings).") 
// prints "There are millions and millions of stars in the Milky Way." 

元組 (Tuple)

你可以使用元組在同一個switch語句中測試多個值。元組中的元素可以是值贸桶,也可以是范圍。另外桌肴,使用下劃線(_)來匹配所有可能的值皇筛。

下面的例子展示了如何使用一個(Int, Int)類型的元組來分類下圖中的點(x, y):

let somePoint = (1, 1) 
switch somePoint { 
case (0, 0): 
    println("(0, 0) is at the origin") 
case (_, 0): 
    println("(\(somePoint.0), 0) is on the x-axis") 
case (0, _):println("(0, \(somePoint.1)) is on the y-axis") 
case (-2...2, -2...2): 
    println("(\(somePoint.0), \(somePoint.1)) is inside the box") 
default:println("(\(somePoint.0), \(somePoint.1)) is outside of the box") 
} 
// prints "(1, 1) is inside the box" 

不像C語言,Swift 允許多個case匹配同一個值坠七。實際上水醋,在這個例子中,點(0, 0)可以匹配所有四個case彪置。但是拄踪,如果存在多個匹配,那么只會執(zhí)行第一個被匹配到的case塊拳魁』掏考慮點(0, 0)會首先匹配case (0, 0),因此剩下的能夠匹配(0, 0)的case塊都會被忽視掉潘懊。

值綁定 (Value Bindings)

case塊的模式允許將匹配的值綁定到一個臨時的常量或變量姚糊,這些常量或變量在該case塊里就可以被引用了——這種行為被稱為值綁定。

下面的例子展示了如何在一個(Int, Int)類型的元組中使用值綁定來分類下圖中的點(x, y):

let anotherPoint = (2, 0) 
switch anotherPoint { 
case (let x, 0): 
    println("on the x-axis with an x value of \(x)") 
case (0, let y): 
    println("on the y-axis with a y value of \(y)") 
case let (x, y): 
    println("somewhere else at (\(x), \(y))") 
} 
// prints "on the x-axis with an x value of 2" 

這三個case都聲明了常量x和y的占位符授舟,用于臨時獲取元組anotherPoint的一個或兩個值救恨。第一個case——case (let x, 0)將匹配一個縱坐標為0的點,并把這個點的橫坐標賦給臨時的常量x释树。類似的肠槽,第二個case——case (0, let y)將匹配一個橫坐標為0的點擎淤,并把這個點的縱坐標賦給臨時的常量y。

一旦聲明了這些臨時的常量秸仙,它們就可以在其對應(yīng)的case塊里引用嘴拢。

請注意,這個switch語句不包含默認塊筋栋。這是因為最后一個case——case let(x, y)聲明了一個可以匹配余下所有值的元組炊汤。這使得switch語句已經(jīng)完備了,因此不需要再書寫默認塊弊攘。

在上面的例子中抢腐,x和y是常量,這是因為沒有必要在其對應(yīng)的case塊中修改它們的值襟交。然而迈倍,它們也可以是變量——程序?qū)?chuàng)建臨時變量,并用相應(yīng)的值初始化它捣域。修改這些變量只會影響其對應(yīng)的case塊啼染。

Where

case塊的模式可以使用where語句來判斷額外的條件。

下面的例子把下圖中的點(x, y)進行了分類:

let yetAnotherPoint = (1, -1) 
switch yetAnotherPoint { 
case let (x, y) where x == y: 
    println("(\(x), \(y)) is on the line x == y") 
case let (x, y) where x == -y: 
    println("(\(x), \(y)) is on the line x == -y") 
case let (x, y): 
    println("(\(x), \(y)) is just some arbitrary point") 
} 
// prints "(1, -1) is on the line x == -y" 

Labeled Statements
產(chǎn)生一個帶標簽的語句是通過在該語句的關(guān)鍵詞的同一行前面放置一個標簽焕梅,并且該標簽后面還需帶著一個冒號迹鹅。下面是一個while循環(huán)體的語法,同樣的規(guī)則適用于所有的循環(huán)體和switch代碼塊贞言。

label name: while condition { 
    statements 
} 

如:

gameLoop: while square != finalSquare { 
    if ++diceRoll == 7 { diceRoll = 1 } 
    switch square + diceRoll { 
    case finalSquare: 
        // diceRoll will move us to the final square, so the game is over 
        break gameLoop 
    case let newSquare where newSquare > finalSquare:          // diceRoll will move us beyond the final square, so roll again 
        continue gameLoop 
    default:// this is a valid move, so find out its effect square += diceRoll  square += board[square] } 
} 
println("Game over!") 

break gameLoop語句跳轉(zhuǎn)控制去執(zhí)行while循環(huán)體后的第一行代碼斜棚,while結(jié)束,游戲結(jié)束该窗。

continue gameLoop語句結(jié)束本次while循環(huán)的迭代弟蚀,開始下一次循環(huán)迭代。

NOTE:如果上述的break語句沒有使用gameLoop標簽酗失,那么它將會中斷switch代碼塊而不是while循環(huán)體义钉。使用gameLoop標簽清晰的表明了break想要中斷的是哪個代碼塊。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末规肴,一起剝皮案震驚了整個濱河市捶闸,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌奏纪,老刑警劉巖鉴嗤,帶你破解...
    沈念sama閱讀 217,542評論 6 504
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異序调,居然都是意外死亡醉锅,警方通過查閱死者的電腦和手機,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,822評論 3 394
  • 文/潘曉璐 我一進店門发绢,熙熙樓的掌柜王于貴愁眉苦臉地迎上來硬耍,“玉大人垄琐,你說我怎么就攤上這事【瘢” “怎么了狸窘?”我有些...
    開封第一講書人閱讀 163,912評論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長坯认。 經(jīng)常有香客問我翻擒,道長,這世上最難降的妖魔是什么牛哺? 我笑而不...
    開封第一講書人閱讀 58,449評論 1 293
  • 正文 為了忘掉前任陋气,我火速辦了婚禮,結(jié)果婚禮上引润,老公的妹妹穿的比我還像新娘巩趁。我一直安慰自己,他們只是感情好淳附,可當我...
    茶點故事閱讀 67,500評論 6 392
  • 文/花漫 我一把揭開白布议慰。 她就那樣靜靜地躺著,像睡著了一般奴曙。 火紅的嫁衣襯著肌膚如雪别凹。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,370評論 1 302
  • 那天洽糟,我揣著相機與錄音番川,去河邊找鬼。 笑死脊框,一個胖子當著我的面吹牛,可吹牛的內(nèi)容都是我干的践啄。 我是一名探鬼主播浇雹,決...
    沈念sama閱讀 40,193評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼屿讽!你這毒婦竟也來了昭灵?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,074評論 0 276
  • 序言:老撾萬榮一對情侶失蹤伐谈,失蹤者是張志新(化名)和其女友劉穎烂完,沒想到半個月后,有當?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體诵棵,經(jīng)...
    沈念sama閱讀 45,505評論 1 314
  • 正文 獨居荒郊野嶺守林人離奇死亡抠蚣,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,722評論 3 335
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了履澳。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片嘶窄。...
    茶點故事閱讀 39,841評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡怀跛,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出柄冲,到底是詐尸還是另有隱情吻谋,我是刑警寧澤,帶...
    沈念sama閱讀 35,569評論 5 345
  • 正文 年R本政府宣布现横,位于F島的核電站漓拾,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏戒祠。R本人自食惡果不足惜骇两,卻給世界環(huán)境...
    茶點故事閱讀 41,168評論 3 328
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望得哆。 院中可真熱鬧脯颜,春花似錦、人聲如沸贩据。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,783評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽饱亮。三九已至矾芙,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間近上,已是汗流浹背剔宪。 一陣腳步聲響...
    開封第一講書人閱讀 32,918評論 1 269
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留壹无,地道東北人葱绒。 一個月前我還...
    沈念sama閱讀 47,962評論 2 370
  • 正文 我出身青樓,卻偏偏與公主長得像斗锭,于是被迫代替她去往敵國和親地淀。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 44,781評論 2 354

推薦閱讀更多精彩內(nèi)容