1. 程式人生 > >Disruptor(無鎖併發框架)

Disruptor(無鎖併發框架)

分享到:44

譯者:羅立樹

假如你生活在另外一個星球,我們最近開源了一套高效能的基於訊息傳遞的開源框架。

下面我給大家介紹一下如何將訊息通過Ring buffer在無鎖的情況下進行處理。

在深入介紹之前,可以先快速閱讀一下Trish發表的文章,該文章介紹了ring buffer和其工作原理。

這篇文章的要點如下:

1.ring buffer是由一個大陣列組成的。

2.所有ring buffer的“指標”(也稱為序列或遊標)是java long型別的(64位有符號數),指標採用往上計數自增的方式。(不用擔心越界,即使每秒1,000,000條訊息,也要消耗300,000年才可以用完)。

3.對ring buffer中的指標進行按ring buffer的size取模找出陣列的下標來定位入口(類似於HashMap的entry)。為了提高效能,我們通常將ring buffer的size大小設定成實際使用的2倍。

這樣我們可以通過位運算(bit-mask )的方式計算出陣列的下標。

Ring buffer的基礎結構

注意:和程式碼中的實際實現,我這裡描述的內容是進行了簡化和抽象的。從概念上講,我認為更加方面理解。

ring buffer維護兩個指標,“next”和“cursor”。

basic-structure1

在上面的圖示裡,是一個size為7的ring buffer(你應該知道這個手工繪製的圖示的原理),從0-2的座標位置是填充了資料的。

“next”指標指向第一個未填充資料的區塊。“cursor”指標指向最後一個填充了資料的區塊。在一個空閒的ring bufer中,它們是彼此緊鄰的,如上圖所示。

填充資料(Claiming a slot,獲取區塊)

Disruptor API 提供了事務操作的支援。當從ring buffer獲取到區塊,先是往區塊中寫入資料,然後再進行提交的操作。

假設有一個執行緒負責將字母“D”寫進ring buffer中。將會從ring buffer中獲取一個區塊(slot),這個操作是一個基於CAS的“get-and-increment”操作,將“next”指標進行自增。這樣,當前執行緒(我們可以叫做執行緒D)進行了get-and-increment操作後,

指向了位置4,然後返回3。這樣,執行緒D就獲得了位置3的操作許可權。

after-d-claim2

接著,另一個執行緒E做類似以上的操作。

after-e-claim3

提交寫入

以上,執行緒D和執行緒E都可以同時執行緒安全的往各自負責的區塊(或位置,slots)寫入資料。但是,我們可以討論一下執行緒E先完成任務的場景…

執行緒E嘗試提交寫入資料。在一個繁忙的迴圈中有若干的CAS提交操作。執行緒E持有位置4,它將會做一個CAS的waiting操作,直到  “cursor”變成3,然後將“cursor”變成4。

再次強調,這是一個原子性的操作。因此,現在的ring buffer中,“cursor”現在是2,執行緒E將會進入長期等待並重試操作,直到 “cursor”變成3。

然後,執行緒D開始提交。執行緒E用CAS操作將“cursor”設定為3(執行緒E持有的區塊位置)當且僅當“cursor”位置是2.“cursor”當前是2,所以CAS操作成功和提交也成功了。

這時候,“cursor”已經更新成3,然後所有和3相關的資料變成可讀。

這是一個關鍵點。知道ring buffer填充了多少 – 即寫了多少資料,那一個序列數寫入最高等等,是遊標的一些簡單的功能。“next”指標是為了保證寫入的事務特性。

after-d-commits4

最後的疑惑是執行緒E的寫入可見,執行緒E一直重試,嘗試將“cursor”從3更新成4,經過執行緒D操作後已經更新成3,那麼下一次重試就可以成功了。

after-e-commits5

總結

寫入資料可見的先後順序是由執行緒所搶佔的位置的先後順序決定的,而不是由它的提交先後決定的。但你可以想象這些執行緒從網路層中獲取訊息,這是和訊息按照時間到達的先後順序是沒什麼不同的,而兩個執行緒競爭獲取一個不同循序的位置。

因此,這是一個簡單而優雅的演算法,寫操作是原子的,事務性和無鎖,即使有多個寫入執行緒。

相關推薦

Disruptor(併發框架)-釋出

譯者:羅立樹 假如你生活在另外一個星球,我們最近開源了一套高效能的基於訊息傳遞的開源框架。 下面我給大家介紹一下如何將訊息通過Ring buffer在無鎖的情況下進行處理。 在深入介紹之前,可以先快速閱讀一下Trish發表的文章,該文章介紹了ring buffer和其工作原理。 這篇文章的

Disruptor(併發框架)

分享到:44 譯者:羅立樹 假如你生活在另外一個星球,我們最近開源了一套高效能的基於訊息傳遞的開源框架。 下面我給大家介紹一下如何將訊息通過Ring buffer在無鎖的情況下進行處理。 在深入介紹之前,可以先快速閱讀一下Trish發表的文章,該文章介紹了ring buffer和其工作原理

併發框架Disruptor

概述 Martin Fowler在自己網站上寫了一篇LMAX架構(譯文)的文章,在文章中他介紹了LMAX是一種新型零售金融交易平臺,它能夠以很低的延遲產生大量交易。這個系統是建立在JVM平臺上,其

基於ThreadLocal的併發發號器實現

ThreadLocal是一個執行緒級別的變數副本,它是對於執行緒隔離的,各個執行緒之間不能訪問非自己的ThreadLocal變數。 我們先來分析一下一個優秀的ID應該具備哪些特點? 全域性唯一性 有序性 能夠包含一些資訊(比如說時間資訊、生成機器資訊等) 為

併發等待併發的對比分析

原文地址:作者:rethinkdb  譯者:sooerr 校對:方騰飛 有兩種非阻塞執行緒同步演算法,即無鎖和無等待,這兩種演算法經常會產生混淆。 在無鎖系統中,當任何特定的運算被阻塞的時候,所有CPU可以繼續處理其他的運算。換種方式說,在無鎖系統中,當給定執行緒被其他執行緒阻塞的時候,所有C

Disruptor佇列淺析

    近期在看作業系統相關資料的時候,閱讀到“訊號量與PV操作”,主要分三塊:互斥控制,同步控制,生產者與消費者問題。因為我日常與伺服器及訊息佇列打交道較多,對生產者與消費者問題比較感興趣,正好之前曾經研究過“Disruptor無鎖佇列”的實現原理,正好再結合PV操作重新

環形佇列框架Disruptor不同策略說明

* <pre> * BlockingWaitStrategy: 這是預設的策略,使用BlockingWaitStrategy和使用BlockingQueue是非常類似的, * 他們都使用鎖和條件Condition進行資料的監控和執行緒的喚醒,因為涉及到執行緒的切換,BlockingW

併發框架Disruptor場景應用

轉自 https://blog.csdn.net/qq_19558705/article/details/77247912 今天用一個停車場問題來加深對Disruptor的理解。一個有關汽車進入停車場的問題。當汽車進入停車場時,系統首先會記錄汽車資訊。同時也會發送訊息到其他系統處理相關業

併發框架Disruptor快速入門

轉自https://blog.csdn.net/qq_19558705/article/details/77116949 1. 什麼是Disruptor Disruptor它是一個高效能的非同步處理的開源併發框架,能夠在無鎖的情況下實現網路的Queue併發操作。可以認為是最快的訊息框

Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰(密連結)

第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級資料進行壓力測試。讓大

併發級別:阻塞、無障礙、等待

一般認為併發可以分為阻塞與非阻塞,對於非阻塞可以進一步細分為無障礙、無鎖、無等待,下面就對這幾個併發級別,作一些簡單的介紹。 併發級別 1、阻塞 阻塞是指一個執行緒進入臨界區後,其它執行緒就必須在臨界區外等待,待進去的執行緒執行完任務離開臨界區後,其它執行緒才能再進去。 2、無

Java 多執行緒高併發 2 — CAS

在 Java 併發程式設計裡面,最可愛的就是無鎖了,非常巧妙,精彩絕倫 額。O__O "… 那麼什麼是無鎖? 顧名思義,在併發情況下采用無鎖的方式實現物件操作的原子性,保證資料一致性、安全性、正確性

某課加密Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰

第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級

Disruptor併發框架(二)

核心術語 RingBuffer(容器): 被看作Disruptor最主要的元件,然而從3.0開始RingBuffer僅僅負責儲存和更新在Disruptor中流通的資料。對一些特殊的使用場景能夠被使用者(使用其他資料結構)完全替代。 Sequence(槽位置): Disruptor

Java併發程式設計高階技術、高效能併發框架Disruptor

1.簡介 Martin Fowler在自己網站上寫了一篇LMAX架構的文章,在文章中他介紹了LMAX是一種新型零售金融交易平臺,它能夠以很低的延遲產生大量交易。這個系統是建立在JVM平臺上,其核心是一個業務邏輯處理器,它能夠在一個執行緒裡每秒處理6百萬訂單。業務邏輯處理器完全是執行在

併發程式設計之高併發場景:秒殺(、排他、樂觀、redis快取的逐步演變)

環境: jdk1.8;spring boot2.0.2;Maven3.3 摘要說明: 在實際開發過程中往往會出現許多高併發場場景,秒殺,強紅包,搶優惠卷等; 其中: 秒殺場景的特點就是單位時間湧入使用者量極大,商品數少,且要保證不可超量銷售; 秒殺產品的本質就是減

Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰加密

第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級

Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰加密分享

第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級

併發程式設計(三): 使用C++11實現stack(lock-free stack)

C++11中CAS實現: template< class T> struct atomic { public: bool compare_exchange_weak( T& expected, T desired,                    

Java併發程式設計高階技術-高效能併發框架原始碼解析與實戰最新加密

第1章 課程介紹(Java併發程式設計進階課程) 什麼是Disruptor?它一個高效能的非同步處理框架,號稱“單執行緒每秒可處理600W個訂單”的神器,本課程目標:徹底精通一個如此優秀的開源框架,面試秒殺面試官。本章會帶領小夥伴們先了解課程大綱與重點,然後模擬千萬,億級