Select 語句和 Swithc 語句的句式十分相似片迅,但是 Select 中的 Case 必須是一個通信操作(一個 Channel 操作)。其執(zhí)行邏輯是:哪一個 Case 后面的 Channel 操作可以被成功執(zhí)行签则,則執(zhí)行該 Case 下的代碼塊靴庆。如果同時多個 Case 可被成功執(zhí)行册养,則隨機(jī)選擇其中一個构拳。如果所有 Case 均不可被成功執(zhí)行蕊梧,則執(zhí)行 default 下的代碼塊。如果沒有 default 則會阻塞并返回死鎖錯誤腮介。
在學(xué)習(xí)過程中肥矢,看到一些文章寫到 select 語句的作用是
監(jiān)聽 IO 操作,當(dāng) IO 操作發(fā)生時叠洗,觸發(fā)相應(yīng)的動作甘改。
這個說法是對的,監(jiān)聽(Channel 的) IO 操作并作出相應(yīng)動作確實(shí)是 Select 的應(yīng)用場景灭抑,但是千萬不要誤以為 Select 語句是在選擇哪個 case 下的 Channel 操作被執(zhí)行了十艾!這么理解是錯的!Select 真正會選擇的是哪個 case 下的 Channel 操作可以被成功執(zhí)行腾节,則執(zhí)行該 case 下的代碼塊忘嫉。
比如,當(dāng)一個 Channel c1 被寫入一條數(shù)據(jù)
c1 := make(chan string, 1)
c1 <- "Hello World!"
如果我們有以下 Select 判斷語句
select {
case <-c1:
fmt.Println("Case 1 is selected")
case c1<-"Hello World!":
fmt.Println("Case 2 is selected")
default :
fmt.Println("Default is selected")
}
你會得到如下結(jié)果案腺,
Case 1 is selected
因?yàn)?c1 被寫入了一條數(shù)據(jù)庆冕,所以我們可以成功 “從 c1 讀出一條數(shù)據(jù)”。也就是第一個 case 可以被成功執(zhí)行劈榨。所以访递,第一個 case 下的代碼塊最終被執(zhí)行。