Go里面提供了一個關鍵字select,通過select可以監聽channel上的數據流動。
創新互聯建站是一家集網站建設,德陽企業網站建設,德陽品牌網站建設,網站定制,德陽網站建設報價,網絡營銷,網絡優化,德陽網站推廣為一體的創新建站企業,幫助傳統企業提升企業形象加強企業競爭力。可充分滿足這一群體相比中小企業更為豐富、高端、多元的互聯網需求。同時我們時刻保持專業、時尚、前沿,時刻以成就客戶成長自我,堅持不斷學習、思考、沉淀、凈化自己,讓我們為更多的企業打造出實用型網站。
select的用法與switch語言非常類似,由select開始一個新的選擇塊,每個選擇條件由case語句來描述。
與switch語句可以選擇任何可使用相等比較的條件相比,select有比較多的限制,其中最大的一條限制就是每個case語句里必須是一個IO操作,大致的結構如下:
select {
case <-chan1:
// 如果chan1成功讀到數據,則進行該case處理語句
case chan2 <- 1:
// 如果成功向chan2寫入數據,則進行該case處理語句
default:
// 如果上面都沒有成功,則進入default處理流程
}
在一個select語句中,Go語言會按順序從頭至尾評估每一個發送和接收的語句。
如果其中的任意一語句可以繼續執行(即沒有被阻塞),那么就從那些可以執行的語句中任意選擇一條來使用。
如果沒有任意一條語句可以執行(即所有的通道都被阻塞),那么有兩種可能的情況:
l 如果給出了default語句,那么就會執行default語句,同時程序的執行會從select語句后的語句中恢復。
l 如果沒有default語句,那么select語句將被阻塞,直到至少有一個通信可以進行下去。
示例代碼:
func fibonacci(c, quit chan int) {
x, y := 1, 1
for {
select {
case c <- x:
x, y = y, x+y
case <-quit:
fmt.Println("quit")
return
}
}
}
func main() {
c := make(chan int)
quit := make(chan int)
go func() {
for i := 0; i < 6; i++ {
fmt.Println(<-c)
}
quit <- 0
}()
fibonacci(c, quit)
}
運行結果如下:
有時候會出現goroutine阻塞的情況,那么我們如何避免整個程序進入阻塞的情況呢?我們可以利用select來設置超時,通過如下的方式實現:
func main() {
c := make(chan int)
o := make(chan bool)
go func() {
for {
select {
case v := <-c:
fmt.Println(v)
case <-time.After(5 * time.Second):
fmt.Println("timeout")
o <- true
break
}
}
}()
//c <- 666 // 注釋掉,引發 timeout
<-o
}
代碼如下所示:
// code_049_select_and_timeout project main.go
package main
import (
"fmt"
"time"
)
/*
1)Go里面提供了一個關鍵字select,通過select可以監聽channel上的數據流動。
2)select的用法與switch語言非常類似,由select開始一個新的選擇塊,每個選擇條件由case語句來描述。
3)與switch語句可以選擇任何可使用相等比較的條件相比, select有比較多的限制,其中最大的一條限制就是每個case語句里必須是一個IO操作
*/
func fibonacci(c, quit chan int) {
x, y := 1, 1
for {
select {
case c <- x: //此處執行了發送,如果成功向c寫入數據,則進行該case處理語句
x, y = y, x+y
case <-quit: //此處執行了接收, 如果quit成功讀到數據,則進行該case處理語句
//從輸出結果可以看到, 此代碼一直不斷地向channel中寫入數據。 在main函數中只是讀取6個數據, 而寫入的數據多于讀取的數據
fmt.Println("quit:y=", y)
return
}
}
}
func main() {
//1) select的使用
c1 := make(chan int)
quit := make(chan int)
go func() {
for i := 0; i < 6; i++ {
fmt.Println(<-c1) //讀取數據
}
quit <- 0
}()
fibonacci(c1, quit)
//2) goroutine阻塞,利用select設置超時
c := make(chan int)
o := make(chan bool)
go func() {
for {
select {
case v := <-c:
fmt.Println(v)
case <-time.After(5 * time.Second): //返回值為channel類型,輸出值為Time當前時間
fmt.Println("timeout")
o <- true
break
}
}
}()
//c <-666 //注釋掉,引發timeout
<-o
}
新聞標題:golang中select和超時
本文路徑:http://vcdvsql.cn/article18/jhipdp.html
成都網站建設公司_創新互聯,為您提供云服務器、網站改版、網站排名、關鍵詞優化、動態網站、品牌網站制作
聲明:本網站發布的內容(圖片、視頻和文字)以用戶投稿、用戶轉載內容為主,如果涉及侵權請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網站立場,如需處理請聯系客服。電話:028-86922220;郵箱:631063699@qq.com。內容未經允許不得轉載,或轉載時需注明來源: 創新互聯