Go和C語言的32 位的無鎖、併發、通用佇列的原始碼
在考慮併發佇列設計時,我想到了一個通用的、無鎖的佇列,它適合於32位整數。這個佇列是 "通用 "的,因為一個單一的實現支援任何任意型別的元素,儘管它是用C語言實現的。它是無鎖的,因為它保證了全系統的進度。它一次最多可以儲存32,767個元素--對於必須始終保持約束的訊息佇列來說,這已經足夠了。
我將首先介紹一個單消費者、單生產者的佇列,然後以一定的代價將支援擴充套件到多個消費者。
佇列只有32位,怎麼能儲存這麼多元素?它只處理一個迴圈緩衝區的索引。呼叫者負責分配和操作佇列的儲存,在單一消費者的情況下,這不需要任何花哨的東西。同步是由佇列管理的。
像一個典型的圓形緩衝區,它有一個頭部索引和一個尾部索引。頭部是下一個要推送的元素,而尾部是下一個要彈出的元素。佇列儲存必須有兩個冪的長度,但容量比長度少一個。如果頭和尾相等,那麼佇列就是空的。這就 "浪費 "了一個元素,這就是為什麼容量比儲存的長度少一個。因此,這種設計已經有了一些明顯的限制,但我相信這種佇列的主要用例--用於CPU繫結的作業佇列--對這些限制沒有問題。
由於這是一個併發的佇列,值得注意的是儲存元素的 "所有權"。消費者擁有從尾部到頭部的元素,但不包括頭部。生產者擁有其他一切。推送和彈出都涉及一個 "提交 "步驟,將一個元素的所有權轉移到另一個執行緒。沒有元素被同時訪問,這使得任何一個呼叫者的事情都很容易。
單消費者佇列和多消費者佇列都支援:
- 原子:C11、GNU、MSC
- 執行緒:pthreads,win32
- 編譯器:GCC、Clang、MSC
- 主機:Linux、Windows、BSD
原始碼:queue.c
C 和 Go 之間共享的併發佇列:queue.go
相關文章
- C語言 簡單的佇列(陣列佇列)C語言佇列陣列
- Go語言 | 併發設計中的同步鎖與waitgroup用法GoAI
- GO語言併發Go
- 佇列的併發使用佇列
- Go語言是徹底的面向組合的併發語言Go
- 無鎖佇列佇列
- Go語言的互斥鎖MutexGoMutex
- GO 語言的併發模式你瞭解多少?Go模式
- 【Golang詳解】go語言中併發安全和鎖Golang
- 實現無鎖的棧與佇列(4)佇列
- 實現無鎖的棧與佇列(3)佇列
- 實現無鎖的棧與佇列(1)佇列
- 實現無鎖的棧與佇列(2)佇列
- go語言與c語言的相互呼叫GoC語言
- 【Java併發】【AQS鎖】鎖在原始碼中的應用JavaAQS原始碼
- Go語言 | CSP併發模型與Goroutine的基本使用Go模型
- c語言的陣列C語言陣列
- 第09章 Go語言併發,Golang併發Golang
- GO安全併發之無鎖原子操作Go
- 圖解--佇列、併發佇列圖解佇列
- 認識無鎖佇列佇列
- Go語言併發程式設計Go程式設計
- Go語言中的併發模式Go模式
- C 語言的 互斥鎖、自旋鎖、原子操作
- [一起讀原始碼]走進C#併發佇列ConcurrentQueue的內部世界 — .NET Core篇原始碼C#佇列
- GO語言————7.6 字串、陣列和切片的應用Go字串陣列
- Go和Rust都是系統語言和通用語言 - RedditGoRust
- 【JavaSE】Lock鎖,獨佔鎖ReentrantLock的AQS原始碼,如何管理同步佇列。acquire方法和release方法JavaReentrantLockAQS原始碼佇列UI
- 第一次體驗併發語言 Go 和 PHP 的區別GoPHP
- 從JDK原始碼角度看併發鎖的優化JDK原始碼優化
- C語言的本質(32)——C語言與彙編之C語言內聯彙編C語言
- GCD 併發佇列GC佇列
- Java併發包原始碼學習系列:基於CAS非阻塞併發佇列ConcurrentLinkedQueue原始碼解析Java原始碼佇列
- 十九、Go語言基礎之併發Go
- Go 語言併發程式設計之互斥鎖詳解 sync.MutexGo程式設計Mutex
- Go 語言的原子操作和互斥鎖的區別Go
- 實現無鎖的棧與佇列(5):Hazard Pointer佇列
- 併發程式設計 —— 原始碼分析公平鎖和非公平鎖程式設計原始碼