跳转到正文
buybitcoinsmart

术语表 /挖矿与共识

默克尔树

默克尔树是什么?
默克尔树是一种哈希金字塔,它将区块中的每笔交易压缩为一个32字节的值,因此无需其余交易即可证明其中任意一笔付款。

将交易哈希两两配对,对每一对计算哈希,如此重复,直到只剩一个哈希。这个唯一的值被写入区块头,而要证明某笔交易属于该区块,只需沿一条路径取得相关哈希:对于包含2,000笔付款的区块,只需十一个哈希,共352字节。这就是手机钱包无需下载区块即可核实您的比特币已到账的原因。

运作方式

默克尔树将一个列表变成金字塔:逐层把相邻的哈希合并计算,直到只剩一个哈希。

叶子节点是交易 ID,顺序与矿工排列它们的顺序一致。比特币合并每一对时,先将两个32字节的值拼接,再对结果连续两次运行 SHA-256。当某一层的条目数为奇数时,最后一个条目会与自身的副本配对。这使算法保持简单,也曾引发真实的问题:编号为 CVE-2012-2459的漏洞于2012年5月披露,并在当月修复,它利用这种复制构造出一个区块,使节点认为该区块无效,而其中的底层交易本身并无问题。

其好处是对数级的。交易数量翻倍只会增加一层,而不是为每笔交易增加一个哈希。包含1,024笔付款的区块,证明归属需要十个哈希,共320字节。包含四千零九十六笔付款的区块需要十二个哈希,共384字节。验证证明的一方自下而上重新计算这条路径,并将结果与自己已从区块头中信任的根进行比较;不破解 SHA-256,就无法伪造一条路径。

这一切并非起源于比特币。Ralph Merkle 在后来成为 US 4,309,569的专利申请中描述了这一构造,该申请于1979年提交,并于1982年1月获得授权。白皮书引用了他的成果,并将这棵树用于两个目的:在第7节中,从旧区块中修剪已花费的交易以节省磁盘空间;在第8节中,让客户端只持有区块头即可验证一笔付款。

在哪里会遇到它

凡是系统需要在不传送整个集合的情况下证明某个条目属于一个大集合,就会出现默克尔树。

在比特币内部,每个区块头都带有一棵默克尔树的顶端。节点根据收到的交易重建这棵树,如果结果不一致,就拒绝该区块。Bitcoin Core 直接开放了这套机制:gettxoutproof 会生成一份序列化的证明,证明某笔交易已包含在某个区块中,verifytxoutproof 则用于检查这样的证明,这是向他人出示付款证据而无需交出钱包的实用方式。

在比特币的其他部分,Taproot 构建了第二棵这样的树:Taproot 输出的备选花费条件被排列成一棵树,因此披露您所用的分支,不会泄露任何未使用分支的信息。在比特币之外,同样的结构也是 Git 提交历史、用于发现错误签发网站证书的 Certificate Transparency 日志,以及 ZFS 文件系统数据完整性检查的基础。

对钱包用户而言,可见的影响虽小却有用。一个只保存几十兆字节区块头的轻量客户端,可以确认您的交易位于特定区块、处于特定深度;只有当有人在伪造的链上产出了有效的工作量证明(这需要真实的资金成本)时,它才会得到错误的答案。

默克尔树 vs 默克尔根

默克尔树是工作用的结构;默克尔根则是事后保留下来的那个唯一的值。节点在验证区块时在内存中构建整座金字塔,随后将其丢弃,只存储最终位于顶端的那32字节,因为下面的一切都可以根据交易重新生成。当区块浏览器向您显示名为默克尔根的字段时,它就是留存下来的那个值。没有人存储这棵树,也没有人需要这样做。

请勿混淆

常见问题

为什么比特币使用默克尔树,而不是对整个交易列表计算哈希?

因为对列表计算单个哈希,只能证明您持有完整的列表。而树结构只需约十几个哈希,就能证明某笔交易属于某个区块,轻量钱包正是因此才成为可能。

默克尔证明有多大?

树的每一层约32字节。包含2,000笔交易的区块需要十一层,因此一份证明约为352字节,小到足以通过缓慢的移动网络连接发送。

接着阅读

相关术语

挖矿与共识中的更多术语

阅读本页英文版