在Go語言中,有一種特殊的通道類型叫做Buffered Channel(緩衝通道),它在通道中儲存一定數量的元素。當通道中的元素數量達到設定的上限時,寫入操作會被阻塞住,直到有其他協程從通道中讀取元素。相反,當通道中的元素數量為零時,讀取操作也會被阻塞住,直到有其他協程向通道中寫入元素。這種阻塞機制可以有效控制協程之間的同步和通訊。在本文中,我們將詳細介紹Go語言中Buffered Channel的阻塞機制。
問題內容
在《Tour of Go》中,範例程式碼是這樣給出的:
package main import "fmt" func main() { ch := make(chan int, 2) ch <- 1 ch <- 2 fmt.Println(<-ch) fmt.Println(<-ch) }
它執行良好並印出來
1 2
此行為與此練習的描述不同,其中指出:
<code> Sends to a buffered channel block only when the buffer is full. Receives block when the buffer is empty </code>
在ch 行之後,<code>ch
is 已滿,並且由於我們只運行1 個單獨的Goroutine,即主Goroutine,因此該Goroutine 應該被阻塞,直到ch
is 被接收者消耗,因此程式碼不應該到達fmt.Println( 行,但應該說類似
<code> fatal error: all goroutines are asleep - deadlock! </code>
但是,由於情況並非如此,我很困惑,並尋求指導。
這是我寫的另一段程式碼
chh := make(chan int, 2) go func() { chh <- 1 fmt.Printf("chh after 1: %v, %v\n", cap(chh), len(chh)) chh <- 2 fmt.Printf("chh after 2: %v, %v\n", cap(chh), len(chh)) chh <- 3 fmt.Printf("chh after 3: %v, %v\n", cap(chh), len(chh)) }() fmt.Println(<-chh) fmt.Println(<-chh) fmt.Println(<-chh)
執行結果為
1 chh after 1: 2, 0 chh after 2: 2, 0 chh after 3: 2, 1 2 3
這更令人困惑。這次有另一個 goroutine 進行發送。我的期望是,在第一個 fmt.Println( 期間,主 goroutine 應該被阻塞。調度程序將選擇運行匿名函數的 goroutine,並且它應該執行到 <code>chh ,然後它會阻塞自身,調度程序再次恢復到主 goroutine。然而,如結果所示,第二個 goroutine 在 <code>chh 之後立即被阻塞。為什麼會這樣呢?
編輯: 我仍然不明白為什麼我的本地首先打印 1 。當我在遠端伺服器上嘗試使用 go Playground 時,它顯示出不同的行為,現在與我的期望一致。
已知channel是由3個佇列組成(接收goroutines、發送goroutines ans value buffer),當匿名函式執行時,channel chh
的狀態為(sending:empty,valuebuffer: empty,receiving:[main] )
。
正在運行的子 Goroutine 只是將值直接推入主 Goroutine,而沒有實際將其傳遞到值緩衝區。這就是為什麼chh
推送後1
的長度是0
。
解決方法
該通道可容納兩人。兩次發送可以成功而不會阻塞。 第三個不能。只有當通道在發送之前已滿時,發送才會阻塞。
以上是Go 的 Buffered Channel 的阻塞機制的詳細內容。更多資訊請關注PHP中文網其他相關文章!

Golang在实际应用中表现出色,以简洁、高效和并发性著称。1)通过Goroutines和Channels实现并发编程,2)利用接口和多态编写灵活代码,3)使用net/http包简化网络编程,4)构建高效并发爬虫,5)通过工具和最佳实践进行调试和优化。

Go語言的核心特性包括垃圾回收、靜態鏈接和並發支持。 1.Go語言的並發模型通過goroutine和channel實現高效並發編程。 2.接口和多態性通過實現接口方法,使得不同類型可以統一處理。 3.基本用法展示了函數定義和調用的高效性。 4.高級用法中,切片提供了動態調整大小的強大功能。 5.常見錯誤如競態條件可以通過gotest-race檢測並解決。 6.性能優化通過sync.Pool重用對象,減少垃圾回收壓力。

Go語言在構建高效且可擴展的系統中表現出色,其優勢包括:1.高性能:編譯成機器碼,運行速度快;2.並發編程:通過goroutines和channels簡化多任務處理;3.簡潔性:語法簡潔,降低學習和維護成本;4.跨平台:支持跨平台編譯,方便部署。

關於SQL查詢結果排序的疑惑學習SQL的過程中,常常會遇到一些令人困惑的問題。最近,筆者在閱讀《MICK-SQL基礎�...

golang ...

Go語言中如何對比並處理三個結構體在Go語言編程中,有時需要對比兩個結構體的差異,並將這些差異應用到第�...


熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

AI Hentai Generator
免費產生 AI 無盡。

熱門文章

熱工具

Dreamweaver Mac版
視覺化網頁開發工具

MantisBT
Mantis是一個易於部署的基於Web的缺陷追蹤工具,用於幫助產品缺陷追蹤。它需要PHP、MySQL和一個Web伺服器。請查看我們的演示和託管服務。

SAP NetWeaver Server Adapter for Eclipse
將Eclipse與SAP NetWeaver應用伺服器整合。

VSCode Windows 64位元 下載
微軟推出的免費、功能強大的一款IDE編輯器

PhpStorm Mac 版本
最新(2018.2.1 )專業的PHP整合開發工具