当你打开比特币(Bitcoin)网络的区块链浏览器,在少数情况下你或许能够惊讶地发现刚刚产出的一个区块是个“空区块”,就像高度为 825999 的区块一样。严格来说,这样的区块并不完全空,而是除了区块奖励交易(coinbase transaction)以外,区块内不含有任何其他交易。
理想情况下,当矿工获得一个区块的记账权后,矿工获得的收益主要来自两部分:一是区块奖励,即 coinbase 交易;另一部分则是来自在区块中包含交易所获得的手续费收益。对于这种“空区块”来讲,从经济上看起来矿工是损失了一部分收益的,但事实上并非如此……我们今天就来讨论一下这样的区块的产生原理。
矿池是如何与矿工协作的
比特币(Bitcoin)网络的挖矿是一种通过暴力计算符合条件的哈希值来实现工作量证明(Proof of Work,PoW)的过程,其难度如今已经变得很大。就拿上述的 825999 区块举例,该区块产出当时的全网难度约为 73.20 T。这是什么概念呢?如果一个矿工拥有一个 1Ghash/s 效率的计算设备(这比常规的家用显卡效率快得多),那么他需要约 3638791736 天(99693 个世纪!)才能成功挖掘到一个区块。这几乎是不可能独立完成的。
相关代码
python3 -c "print(73.20*10**12 * 2**32 / 10**9 / 60 / 60.0 / 24)"
因此我们有了矿池。矿池按照特定的分配方式(如,按工作量以及最近收益的移动平均值)为参与计算的矿工按照所贡献的算力分配挖矿所获得的收益(与此同时,矿池自己也会获得分成)。为了计算一个区块的目标哈希值,矿工必须首先从矿池获得区块中包含的交易信息等内容后,再通过调整区块中的随机数(nonce)等值,尝试计算出符合目标要求的哈希值。区块中包含的交易数量可能很多(从区块链浏览器来看的话,一个区块中可以容纳 4,000 笔交易,有时候还要更多),因此典型上来讲,矿池可能需要几秒中的时间才能将这些编排的交易内容(矿工待解的“谜题”)整理并发送给矿工(其中还有网络传输时间以及网络延迟)。
空区块的经济学博弈
绝大多数比特币矿工遵循最长链(Longest chain)原则工作:当矿工得知网络上有一个新的有效区块被发现时,矿工会希望基于这个最新产生的区块继续计算下一个区块的哈希。但前面我们提到,完整的下一个区块的信息可能需要几秒钟时间才能传输到矿工本地以供计算。在此期间,为了不浪费矿工宝贵的时间(以及算力),矿池通常会(预先)发送给矿工一个区块的模版信息,该信息是只包含一个区块奖励交易(coinbase transaction)的最小区块数据,以供矿工立刻开始计算。而完整的待计算区块的数据将在之后很快的时间发送给矿工。有的时候,幸运的矿工会在这(短暂的)几秒钟时间内,就基于这个最小的区块模版,计算出下一个有效的区块的结果。这个时候会发生什么?大多数矿工会选择将这个“空区块”广播到区块链网络,以获得该区块中的区块奖励。
在上面的场景中,当矿工计算出一个有效的“空区块”后,矿工虽然无法获得由于包含其他交易所带来的手续费奖励,但是矿工广播交易至少会获得确定性的由新区块带来的奖励。同样地,矿工还面临着其他矿工也计算出有效区块的压力,对手矿工可能会先于自己将另外一个有效的区块广播到网络中。因此,面对一个确定性的(但是可能较少)的奖励,以及另一个有极大不确定性的较多的奖励时,我想绝大多数矿工都会选择广播自己计算出的第一个区块的。
值得注意的是,这样的区块由于不会包含其他任何的交易信息,并且还在区块链中占用了一个区块的位置,会被一些社区成员认为是一种垃圾信息以及对比特币网络的攻击。针对这一点,有一篇发布于 LinkedIn 上的文章很好地讨论了这一点。文章中认为,尽管“空区块”不处理任何内存池中的等待交易,但它们并没有为区块链网络天价更多混乱,反而增强了所有先前区块的安全性,并重申了矿工们维护网络完整性的承诺。“空区块”实际上是对比特币巧妙激励结构的证明。在这个系统中,每个决定,即使是区块中没有交易,也都有助于网络的整体强度和韧性。空区块并不常见,通常不是攻击,也不是垃圾邮件,它们是矿工的战略决策,凸显了比特币架构中内嵌的韧性和远见。