做者:景辰
連接:https://www.zhihu.com/question/22399196/answer/201836128
來源:知乎
著做權歸做者全部。商業轉載請聯繫做者得到受權,非商業轉載請註明出處。
算法
對比特幣熟悉的朋友必定都知道,買賣比特幣最後都是經過一個錢包地址來實現的,就像咱們平常使用的銀行卡卡號,咱們隨便找一個比特幣的錢包地址,你們看一下:編碼
1QCXRuoxWo5Bya9NxHaVBArBQYhatHJrU7加密
可是當談到比特幣的錢包地址是如何算出來的時候,可能就不多有人可以說清楚了。3d
下面,景辰經過實際計算,來給你們講解一下比特幣的錢包地址是怎麼來的,公鑰、私鑰是怎麼來的,以及他們三者之間的關係。blog
下面的過程你不必定懂得轉換的原理,知道他們流轉的過程就能夠了。數學
衆所周知,比特幣是創建在數學加密學基礎上的,而不是像銀行卡那樣是基於信用的,基於信用體系的銀行卡卡號咱們都熟悉,是咱們在向銀行申請銀行卡的時候銀行給隨機發的,那麼比特幣的錢包地址是怎麼來的呢?io
在《比特幣:一種點對點的電子現金系統》一文中,中本聰提到了用橢圓加密算法(ECDSA)來產生比特幣的私鑰和公鑰。比特幣
基於橢圓加密的原理,由私鑰是能夠計算出公鑰的,再由公鑰通過一系列數字簽名運算就會獲得比特幣錢包地址。基礎
由於由公鑰能夠算出比特幣地址,因此咱們常常把公鑰和比特幣地址的說法相混淆,他們都是指的同一個概念,比特幣錢包地址只是另外一種格式的公鑰,可是二者的外在表現形式是不同的。原理
那麼咱們就能夠梳理出一個脈絡了:
私鑰 —— 公鑰 —— 比特幣錢包地址
從比特幣私鑰獲得咱們平常轉帳所用的比特幣錢包地址總共須要九個步驟,中間用到了SHA256加密、RIPEMD160加密和BASE58編碼。
下面,咱們以實際案例來模擬一下整個流程:
第一步:生成隨機私鑰
私鑰是一個隨機數,隨機選取一個32字節的數,這個數的範圍大小是介於1 ~ 0xFFFF FFFF FFFF FFFF FFFF FFFF FFFF FFFE BAAE DCE6 AF48 A03B BFD2 5E8C D036 4141之間的一個數,爲了方便後面的計算,咱們隨機生成一個合法的私鑰:
8F72F6B29E6E225A36B68DFE333C7CE5E55D83249D3D2CD6332671FA445C4DD3
第二步:橢圓曲線算公鑰
生成了私鑰以後,咱們使用橢圓曲線加密算法(ECDSA-secp256k1)計算私鑰所對應的非壓縮公鑰,生成的公鑰共65字節, 其中一個字節是0x04,其中32個字節是X座標,另外32個字節是Y座標:
公鑰P.X:
06CCAE7536386DA2C5ADD428B099C7658814CA837F94FADE365D0EC6B1519385
公鑰P.Y:
FF83EC5F2C0C8F016A32134589F7B9E97ACBFEFD2EF12A91FA622B38A1449EEB
第三步:計算公鑰的SHA-256哈希值
將上述公鑰地址拼合,獲得標準地址:
0406CCAE7536386DA2C5ADD428B099C7658814CA837F94FADE365D0EC6B1519385FF83EC5F2C0C8F016A32134589F7B9E97ACBFEFD2EF12A91FA622B38A1449EEB
對齊進行SHA-256哈希計算,獲得結果:
2572e5f4a8e77ddf5bb35b9e61c61f66455a4a24bcfd6cb190a8e8ff48fc097d
第四步:計算 RIPEMD-160哈希值
取上一步結果,進行RIPEMD-160計算,獲得結果:
0b14f003d63ab31aef5fedde2b504699547dd1f6
第五步:加入地址版本號(比特幣主網版本號「0x00」)
取上一步結果,在前面加上16進制的00,即:
000b14f003d63ab31aef5fedde2b504699547dd1f6
第六步:計算 SHA-256 哈希值
取上一步結果,進行SHA-256計算,可得:
ddc2270f93cc84cc6869dd373f3c340bbf5cb9a8f5559297cc9e5d947aab2536
而後,對以上結果再次計算 SHA-256 哈希值,獲得:
869ac57b83ccf75ca9da8895823562fffb611e3c297d9c2d4612aeeb32850078
第七步:取上一步結果的前4個字節(8位十六進制)
869ac57b
第八步:把這4個字節加在第五步的結果後面
做爲校驗位,將這4個字節加載第五步的結果後面,這就是比特幣地址的16進制形態了:
869ac57b000b14f003d63ab31aef5fedde2b504699547dd1f6
第九步:用Base58編碼變換一下地址
對上一步的結果進行Base58編碼,獲得:
1QCXRuoxWo5Bya9NxHaVBArBQYhatHJrU7
這就是咱們常常看到的傳統意義上的比特幣錢包地址了。
以上步驟能夠簡化爲下圖所示:
咱們常常說的比特幣公鑰就是指的圖中第二步所產生的結果,而HASH160指的是第四步RIPEMD160簽名所產生的結果,因爲RIPEMD也是一種HASH算法因此就統稱爲HASH160了,而咱們經常使用的比特幣地址就是通過BASE58編碼後的結果。