接觸區塊鏈的同窗,多少都據說過拜占庭將軍問題,常常看到或聽到:某某區塊鏈使用某某算法解決了拜占庭將軍問題,那麼究竟什麼是拜占庭將軍問題呢?《區塊鏈100講》今天和你們說說什麼是拜占庭將軍問題。算法
這個問題是萊斯利·蘭伯特(Leslie Lamport)等在論文The Byzantine Generals Problem論文提出的,部分原文以下:網絡
We imagine that several divisions of the Byzantine army are camped outside an enemy city, each division commanded by its own general. The generals can communicate with one another only by messenger. After observing the enemy, they must decide upon a common plan of action. However, some of the generals may be traitors, trying to prevent the loyal generals from reaching agreement.併發
**它是描述分佈式系統一致性問題的著名例子。**經過直譯這個論文來理解這個問題仍是比較困難,能夠適當的補充或者添加一些說明來更好地解讀。分佈式
設想在中世紀,拜占庭帝國擁有巨大的財富,周圍鄰邦垂誕已久。但拜占庭高牆聳立,固若金湯,沒有一個單獨的鄰邦可以成功入侵。任何單個鄰邦入侵的都會失敗,同時也有可能自身被其餘鄰邦入侵。拜占庭帝國防護能力如此之強,至少要有一半以上鄰邦同時進攻,纔有可能攻破。ide
然而,若是其中的一個或者幾個鄰邦自己答應好一塊兒進攻,但實際過程出現背叛,那麼入侵者可能都會被殲滅。因而每一方都當心行事,不敢輕易相信鄰國。(其實這與原文所描述有些誤差,但這樣說更易於理解)學習
在拜占庭問題裏,各鄰國最重要的事情是:全部將軍如何能過達成共識去攻打拜占庭帝國。區塊鏈
達成共識並不是坐下來開個會那麼簡單,有的將軍心機深不可測,口是心非,若是有叛徒,可能會出現各類問題:加密
叛徒可能欺騙某些將軍本身將採起進攻行動。遊戲
叛徒可能慫恿其餘將軍行動。ci
叛徒可能迷惑其餘將軍,使他們接受不一致的信息,從而感到迷惑。
咱們這裏假設:
有A、B、C三位將軍,當A發出進攻命令時,B若是是叛徒,他可能告訴C,他收到的是「撤退」的命令。這時C收到一個「進攻」,一個「撤退「,因而C被信息迷惑,而無所適從。
若是A是叛徒。他告訴B「進攻」,告訴C「撤退」。當C告訴B,他收到「撤退」命令時,B因爲收到了「進攻」的命令,而沒法與C保持一致。
叛徒發送先後不一致的進攻提議,被稱爲「拜占庭錯誤」,而可以處理拜占庭錯誤的這種容錯性稱爲「Byzantine fault tolerance」,簡稱爲BFT。
相信你們已經能夠明白這個問題的複雜性了。
正因爲上述緣由,在只有三個角色的系統中,只要有一個是叛徒,即叛徒數等於1/3,拜占庭問題便不可解。
回顧問題,一羣將軍想要實現某一個目標(一致進攻或者一致撤退),可是單獨行動行不通,必須合做, 達成共識;因爲叛徒的存在,將軍們不知道應該如何達到一致。
注意,這裏**「一致性」纔是拜占庭將軍問題探討的內容**,若是原本叛徒數量就已經多到了問題不可解的地步,這個就是「反叛」的問題了;同時,咱們的目標是忠誠的將軍可以達成一致,對於這些忠誠的將軍來講,進攻或者撤退都是能夠的,只要他們可以達成一致就行。
可是,光靠「一致」就能夠解決問題嗎?考慮一下,若是萬事俱備,客觀上每一個忠誠的將軍只要進攻了就必定可以勝利,可是卻由於叛徒的存在他們都「一致的」沒有進攻;反之,條件不利,將軍們不該該進攻,可是卻由於叛徒的存在全部人都「一致的」進攻了。
能夠發現,**只有「一致性」是不足以解決拜占庭將軍問題的,咱們還須要提出一個「正確性」要求。**這個要求是值得斟酌的,由於若是客觀來看或許會有「絕對正確的」判斷,可是針對每個將軍,你們的判斷或許都不相同,咱們如何定義「正確」呢?咱們或許能夠簡單地說,正確就是每一個忠誠的將軍都正確的表達了本身的意思,不會由於叛徒讓別的將軍認爲忠誠的將軍是叛徒而不採用他傳達的消息。
至此,咱們將拜占庭將軍問題簡化成了,全部忠誠的將軍都可以讓別的將軍接收到本身的真實意圖,並最終一致行動;而形式化的要求就是,「一致性」與「正確性」。
若是將問題推廣開來,能夠發現針對一致性和正確性的算法並不要求命令必須是「進攻/撤退」或是「1/0」,而能夠是「發送消息1/發送消息2/待機」或「x/y/z/w」,這意味着拜占庭將軍問題算法能夠爲多種分佈式系統提供啓發,好比電力系統或網絡系統。
因而可知,這個問題說究竟是一個關於一致性和正確性的算法問題,這個算法是針對的是忠誠的將軍,由於叛徒能夠作出任何超出約定的判斷。咱們就是要在有叛徒的干擾下,找到一個抗干擾的算法。
這個問題困擾了科學家們數十年,直到區塊鏈的出現。
如今讓咱們想象一下,給每一個將軍配備一臺電腦(至關於分佈式的節點),下降信息流通成本,讓信息在極短的時間同步到各位將軍。
同時,爲了不信息混亂,一段時間內只能有一位將軍發送信息。
怎麼來肯定哪位將軍發送信息呢?區塊鏈系統通常經過工做量證實(POW)來肯定誰先發言。(工做量證實將在後續文章介紹)
咱們能夠想象這是一個數獨遊戲,哪一個將軍最早解出來,誰就有權先發送信息。通常,數獨的行與列能夠增刪,經過難度的調整保證這個一段時間是一個比較肯定的數值。在比特幣系統上,這個數字就是10分鐘,也就是說比特幣平均約每10分鐘產生一個區塊。
當某個節點發出統一進攻或者撤退的消息後,各個節點收到發起者的消息必須簽名蓋章,確認各自的身份。比特幣在這裏引用現代非對稱加密技術爲這個信息簽名。
這個過程就像一位將軍A在向其餘的將軍(B、C、D…)發起一個進攻提議同樣,將軍B、C、D…看到將軍A簽過名的進攻提議書,若是是誠實的將軍就會馬上贊成進攻提議,而不會發起本身新的進攻提議。
非對稱加密算法的加密和解密使用不一樣的兩個密鑰,這兩個密鑰就是咱們常常聽到的公鑰和私鑰。通常公鑰是公開的,用於加密。而私鑰是用來解密公鑰獲取信息的。好比,將軍A想給將軍B發送消息,爲防止消息泄露,將軍A只須要使用B的公鑰對信息加密,加密的信息只能用B私鑰解密。(非對稱加密算法將在後續文章介紹)
除了加密信息外,同時,信息通過每一個節點都將進行備份,每一個節點都保存了相同的完整數據,以防止少數叛徒篡改。
好了,咱們再來從新走下一下整個過程:
每一個將軍分配了一臺電腦,A將軍第一個解出數獨遊戲擁有了第一個發言權,A發出攻打的信息,並當即廣播至全部將軍,全部人能夠根據A的公鑰來驗證A的身份,確保信息的可信性,併發出本身同意或反對的選票,在全網驗證後得出結果。
因而,一個不可信的信息傳遞,就變成了一個分佈式的可信網絡,參與者都有權發表意見,並在一件事上達成一致。
拜占庭將軍問題也就獲得瞭解決,文章開頭的問題相信你也已經有了答案。本期就講到這裏,下期繼續。
本文內容來源於:百度百科、巴比特、幣行觀察等
如下是咱們的社區介紹,歡迎各類合做、交流、學習:)