商学院首页 > 一分钟看懂区块链 > 比特币与区块链:从原理到应用[2]

比特币与区块链:从原理到应用[2]

发布时间:2019-12-05 13:43作者:fg信息来源:比特财经网阅读数:12431栏目:一分钟看懂区块链

2 比特币与区块链的基本原理


2.1 比特币简介


之前已经介绍过,数字货币的本质就是一个账本。当有交易发生,资金所有权发生转移(或称价值转移),就通过在这个账本上记账来体现。传统货币金融系统,央行承担货币发行的职责,商业银行承担放贷和吸储的职责,每笔交易记录、每个账户余额都存在银行的账本上,银行此时是作为一个中心机构。比特币系统完全运行在互联网上,并没有一个中心机构替用户保存账本。相反,每一个持有比特币、运用比特币完成交易的节点(完全节点)都会在本地保存一份账本,并从网络上接收新的交易数据对自己的账本进行更新。所以说,不同于传统货币交易账本由银行私密保存,比特币的账本是公开的,分布式存储在每一个参与交易的节点上。


比特币系统是一种P2P网络系统,网络中并不存在任何中心节点,所有P2P网络中的节点地位都是相等的,每个节点从网络接收资源和服务的同时也向网络中的其它节点提供资源和服务。想加入比特币网络也很简单,从比特币官方网站下载比特币客户端并安装到自己的计算机,保证本地存储系统有足够的空间来存储公共账本数据,运行比特币客户端并联入互联网,客户端端口会自动连接到若干现有节点,此时这台计算机就可以作为比特币网络中的一个节点存在了。初始加入的比特币节点可以从其它节点接收账本数据并保存下来。比特币网络中的节点时时刻刻都是在动态变化的,一个节点可以随时选择退出,重新加入时只需要连接其它节点并接收它离开期间新增的交易数据就可以。


虽然每个节点都保存有比特币交易账本,但为了保持所有账本副本的一致性,每笔交易只能安排一个节点记账,其它节点同步新增的交易数据。那到底哪个节点拥有记账的资格呢?比特币系统采用了竞争记账的机制。所有节点共同参与一个解方程大赛,由于这个方程解空间巨大且无任何求解的规律可言,每个参与竞赛的节点只能采用随机尝试的办法搜索方程的解。这样一来,解方程大赛就变成了对各节点计算机运算能力的一场考验,拥有最强大运算能力的节点显然可能更快找到解。一旦某个节点率先找到一个满足要求的解,它就抢到了本次竞赛的记账权。这样的解方程竞赛大约每10分钟在全网举行一次,抢到记账权的节点迅速将过去10分钟全网发生的交易数据记录到一个新的区块(区块链的基本单位,可以看成是一个具有特定数据结构的文件),并将这个区块马上向全网分发,网上的其它节点接收到这个区块时,它就意识到本次解方程大赛已经结束了,进而马上停止本轮的解方程竞赛,同时开始下一轮解方程大赛。


比特币交易的过程完全是匿名的。比特币客户端有钱包的功能,比特币钱包并不存储货币,存储的是地址和私钥。根据非对称加密的原理,一对非对称密钥分为公钥和私钥,私钥私密保存,公钥可以公开出来,其它节点想给当前节点加密发送消息时,可以用公钥对消息进行加密,只有拥有私钥的节点才能对消息解密,这样就保证了信息传输不会被泄漏。在比特币网络,每个节点的私钥由钱包加密存储,用户也可以备份成其他形式存储。公钥经双Hash运算得到的字符串,被称为地址,其实就是另一种形式的公钥。一个比特币地址和它对应的私钥就可以看成一个账户,地址可以看做用户名,私钥看做账户密码。拥有私钥的人就拥有这个地址上的所有资金。比特币的账本数据中并不存在账户余额的概念。事实上账本数据中如果用余额字段来表示每个节点拥有的资产,那么余额字段的数据是很容易被恶意篡改的。既然没有余额数据,那么交易时就没有办法通过对相关节点余额字段的修改实现。事实上,比特币交易中“花费”的是在交易中生成的“未使用的交易输出(UTXO)”。每一笔交易转账相当于将一笔钱注册到新的地址上。比特币地址并没有余额,有的是遍布在账本里所有注册在这个地址上的UTXO。相当于这个地址所拥有的资金分布在一笔笔交易记录中。比特币客户端显示的账户余额其实是对账本数据中隶属于当前节点的UTXO逐一统计得到的结果。


2.2 比特币交易


比特币将货币、交易、账本全都变成了一种数据结构,所以看一下一笔交易的数据结构你会更理解。

 

一笔交易可以包含多个输入并形成多个输出。尚未被“花费”的交易输出即UTXO(unspent transaction output),所谓“花费”指将这笔钱注册到其它地址(资金所有权转移)。时间戳标记这笔交易发生的时间。再来看一下交易输)和输入的数据结构。

 

交易输出结构

 

交易输出的数据结构很简单,主要就是资金总量和锁定脚本。资金总量表明了转账了多少钱。锁定脚本其实表明了这笔钱的所有权。锁定脚本里包含的最重要的内容是转账的目标地址,之前我们也介绍过,比特币地址其实就是公钥转换得到的。交易输出里包含了目标地址相当于用公钥给这笔钱(交易输出)上了一把锁,只有唯一那个有对应钥匙(私钥)的用户才可以使用它。

 

交易输入的数据结构,主要包括指向UTXO的指针和解锁脚本。注意到,比特币账本里只有交易输出才记录了资金,交易输入只是使用资金时用的那把钥匙。其中指向UTXO的指针字段表明要“花费”哪个UTXO。解锁脚本包含了用户的私钥,正确的私钥可以解密UTXO锁定脚本中的公钥加密。解锁脚本和锁定脚本一起运行就可以正确使用UTXO完成交易了。

 

交易输入结构

 

现在小李从苏宁购买了一台空调,需要支付0.15比特币,小李的比特币客户端里的钱包模块会从所有注册在小李地址上的UTXO中选出一个数额最合适的,假设最合适的UTXO的面值是0.2比特币。现在,小李的钱包就会创建一笔新的交易,输入就是面值0.2比特币的UTXO,生成一笔0.15比特币的输出(一个UTXO),输出锁定脚本包含苏宁的地址。与此同时生成一笔地址为自己的输出0.04比特币(另一个UTXO),也就是找零。但是这里0.2-0.15-0.04=0.01,剩余的0.01比特币作为交易费用,用来奖励承担记账工作的节点,赢得记账权的节点会自动收集的。

 

2.2.1 交易周期

 

一笔比特币交易的生命周期从它被创建的那一刻开始,节点会将这笔交易在比特币网络上广播,收到这笔交易数据的节点会对交易有效性进行独立检验。检验内容包括语法和数据格式是否有误、交易输入和输出是否为空等等。通过独立验证的交易会被放入节点自己的交易池,同时继续向其它节点广播,没有通过检验的交易直接被拒绝并不再广播。等到这笔交易被网络上的大部分节点验证,可能耗时不到一秒钟,交易会最终被一个挖矿节点验证并记录到区块链上一个还记录有很多其他交易的区块上(挖矿节点:参与解方程大赛并取得当次记账权的节点)。此时这笔交易的交易输出(UTXO)还不能被使用,等到区块链中在这个区块之上又生成足够多的区块,交易才成为区块链总账簿的一部分,这时交易输出UTXO就可以被新的资金拥有者在下一笔交易中使用了,这样就进入下一个交易周期了。

 

2.3 比特币网络与节点


比特币运行在互联网上并采用P2P协议,P2P网络又称对等网络,网络中每个节点的地位都是相等的。比特币设计的核心原则是去中心化,采用P2P网络很好的体现了这个核心原则。虽然比特币网络中每个节点的地位相等,但不同节点的功能还是不一样的。但是,任何节点都包含四个基本功能中的一个或者多个:钱包、矿工、完整区块链、网络路由节点。


所有节点都是网络路由节点,可以对新创建的交易和区块进行验证,对通过验证的交易和区块进行转发。


一个具备全部四个功能的节点被称为全节点。全节点在本地存储完整的区块链数据(账本),可以独立的对交易和区块数据进行验证而不需要依赖于其他节点。

 

全节点

 

全节点同时具备挖矿功能,即参加算力竞赛(解方程大赛)来赢得记账权的能力。之所以称竞争记账权的行为为“挖矿”。这是为了类比于传统实物货币(金、银)的挖掘开采行为。每个在算力竞赛中获胜的节点能够获得一定数量的比特币做奖励,目前是12.5个比特币,奖励的数量大约每4年会减少一半。除全节点之外,也有单独的挖矿节点。

 

全节点同时具备钱包功能。钱包是用来生成并保存地址和私钥,同时创建交易的模块。


相比于全节点,有些节点只存储了部分区块链数据,它通过“简易支付验证(SPV)”的方式来完成交易验证,称为SPV节点或轻量级节点。SPV节点一般具备网络路由节点和钱包功能。为了让智能手机这种资源有限的终端具备比特币交易的能力,SPV节点现在越来越普遍。


2.4 比特币区块链


区块链的英文名字 Block Chain 更容易理解。Block其实是一个常用的数据量大小的度量单位。比如在Linux/Unix系统里有一个数据块(Data Block)的概念,数据块是文件系统读写的最小单元,在Linux/Unix系统中是512个字节,一个文件所占大小就是数据块的整数倍。又比如在Google分布式文件系统HDFS中,也有一个块(Block)的概念,也是数据存储的一个基本单元,不同之处在于HDFS为了提高大数据的效率和集群的吞吐量,将一个块的大小设置成64MB。所以区块链里的“区块”也是指一个数据单元,而“链”其实就是将很多数据单元(区块)一个个串联起来,就像一个链表。但是链表是通过指针将数据串联起来的,而区块链是通过在每个区块中存储前一个区块的唯一标识符来链接的。具体可以看区块和区块头的数据结构。

 

一个区块主要分为两部分:区块头和交易数据。区块头里记录的是这个区块的元数据,具体见区块头数据结构表2-5。交易数据部分记录了从上一个区块被挖出到当前区块被挖出的约10分钟时间内,全网发生的所有比特币交易。比特币系统中一个区块大小并没有严格限制,区块头的大小固定是80个字节,平均每个交易至少是250个字节,而平均每个区块至少包含超过500个交易。交易的数据结构之前已经介绍过,下面来看一下区块头的数据结构。


“父区块哈希值”字段存储了前一个区块数据的Hash值,严格来说,并不是整个区块数据的Hash值,而是区块头数据的Hash值。其实是运用SHA256算法对区块头数据做两次Hash运算得出的。由于每个区块头数据具有唯一性,它的Hash值基本可以作为区块的主标识符。所以将前一个区块(父区块)的标识符存在当前区块的区块头里,也就相当于将这两个区块连接了起来。


“Merkle根”字段相当于是区块内所有交易数据的一个数字指纹,要得到Merkle根先要创建一棵Merkle树。假设现在有A,B,C,D四笔交易,创建的Merkle树图。

 

Merkle树是自底向上创建的,是一种Hash二叉树。首先将交易数据输入SHA256算法得到每笔交易的Hash值Ha、Hb、Hc、Hd,这四个Hash值作为叶子节点,将叶子节点Hash值两两连接起来继续输入SHA256算法可以得到上一层节点的Hash值,计算示例如下。如果叶子节点个数为奇数,将最后一个节点复制一份。

 

Ha=SHA256(SHA256(交易A))

 

Hab=SHA256(SHA256(Ha+Hb))

 

如此循环进行,直到只剩一个节点,也就是Merkle树根。考虑到SHA256算法的特性,Merkle根可以看成是所有交易数据的一个归纳,也可以看成是所有交易数据的数字指纹,因为即使任意交易数据被微小篡改,它生成的Hash值也会有很大变化,而叶子节点Hash值的变化,又会影响从该叶子节点连接到Merkle根的路径上所有节点Hash值的变化,最终使Merkle根产生很大的变化。因此Merkle根可以唯一标识一批交易数据,也可以验证一批交易数据是否被篡改过。由于SHA256算法输出固定是32个字节,所以Merkle树中所有节点包括Merkle树根的值都固定是32个字节。Merkle树在比特币系统中的一个主要用处是可以高效的验证一笔交易是否存在于区块中。假设某区块记录了N笔交易,利用Merkle树可以最多计算2*log2(N)次就可以判断一笔交易是否存在于这个区块中。


区块头数据结构中的“难度目标”字段是用来动态调节挖矿难度的,约两周时间会调整一次,为了保证能够在大概在10分钟左右的时间挖出一个区块(解出方程)。Nonce字段也是在挖矿(解方程大赛)时用到的,Nonce字段的值作为方程未知变量的一部分,不断修改Nonce字段值以获得满足难度目标的解。


区块链就是就是将包含交易信息的区块从后往前依次连接起来的数据结构。它可以存储在文件系统,也可以存储在一个简单数据库。区块链可以被视为一个垂直的栈,第一个区块(创世区块)作为栈的底部,后续创建的区块依次向上叠加,这样就可以用一些术语,“高度”来表示当前区块离第一个区块之间的距离,用“顶部”表示最新生成的区块,用“深度”表示当前区块距离顶部区块的距离。


每个区块的区块头数据经SHA256算法得到区块Hash值,每个区块的区块Hash值并不存在于自身数据当中,而是在创建它的子区块(栈内上一层区块)时临时计算得出并存储在子区块“父区块哈希值”字段中。由于区块Hash值可以在区块链中唯一识别出一个区块,因此通过“父区块哈希值”就可以引用前一个区块。这样就通过“父区块哈希值”字段将每个区块依次链接起来形成了一条一直可以追溯到首区块(创世区块)的链条。每个区块都只有一个父区块,但可能存在多个子区块,这被称为“区块链分叉”。这种情况只在两个矿工几乎同时挖掘出新区块时才可能出现,但也只是暂时存在,很快区块链系统就会选出工作量最大的链条作为主链。

 

区块哈希值虽然只是区块头数据的Hash值,但是区块头中包含的Merkle根字段是对所有交易数据的一个概括。上面介绍过,任何对交易数据的微篡改都会导致Merkle根发生很大变化,进而导致区块哈希值也发生变化。由于子区块会存储父区块的区块哈希值,所以如果父区块任意数据有变动,就会导致子区块数据产生变动,而子区块数据变动又会导致孙区块值发生变动,等等以此类推。很明显,对区块链中任意区块数据的篡改都会导致它后续所有区块的数据发生变动,除非将后续所有区块都重新生成,否则无法修改区块链中的数据。而重新生成区块面临着巨大的工作量(解出每个区块中的方程),当区块的“深度”到达6时,由于巨大的工作量导致实际上想篡改这个区块的数据已经变得不可能。这种区块链历史数据不可更改的特性是区块链可信的一个关键原因。同时,这也是比特币安全性的一个关键原因。


2.5 比特币挖矿

 

将比特币网络中节点之间竞争记账权的行为称为“挖矿”。“挖矿”是比特币系统中一个非常聪明的设计,它同时实现了三个目标:

 

(1)一种激励机制,使得比特币节点有动力去记录交易数据。

 

(2)实现了新币发行。

 

(3)通过工作量证明算法(解方程大赛)使得区块链历史数据实际上不可更改。

 

之前说节点之间竞争记账权其实是在参加每10分钟一场在全网举行的解方程大赛。每场竞赛的获胜者将获得本轮记账权,有权创建一个新区块并将前10分钟全网发生的比特币交易记录到新区块。解方程大赛的规则被一个称为“工作量证明(Proof of Work)”的算法所定义。工作量证明算法定义每轮竞赛中所有挖矿节点独立求解一道包含Hash函数的方程,谁先求出满足难度目标的解,谁就获胜。

 

什么方程?Hash(区块头数据)=满足难度目标的哈希值。

 

其实就是通过不断修改区块头中的Nonce字段值(通常是递增1),使得区块头哈希值满足难度目标。难度目标就是区块头“难度目标”字段值。这个难度目标字段值通常类似于:哈希函数的输出值十六进制表示以0开头。从概率角度看,平均随机尝试16次可以得到一个满足难度目标的解(十六进制数字取值0到F)。从数字角度看,要找一个输出小于0x10000000......0的输入。显然,这个字段的值可以看成一个难度阈值。如果将难度阈值继续降低,要找到一个满足要求的解会变得越来越困难。2014年的时候,一个矿工平均要尝试10^15次才能找到一个合适的Nonce使得区块头信息哈希值足够小。这几年随着计算机运算能力的快速进步,挖矿设备越来越专业,难度阈值也设置的越来越小,才能保证全网10分钟左右挖出一个新区块。难度目标的调整是依据最新的2016个区块(约两周时间)与20160分钟的比较得出的。


挖矿过程中,每次尝试虽然是Nonce值递增,但其实是在随机尝试。这是由哈希函数的三个性质决定的:

 

(1)不可逆。不可能根据哈希函数的输出值反推出输入值。

 

(2)抗碰撞。两个不同的输入值得到相同哈希输出的可能性极低。

 

(3)高灵敏。当输入有微小变化时哈希值输出都会产生巨大的变化。

 

以上三个性质保证在搜索解时,没有办法用前面的前一步经验来指导后续的搜索,只能一直处于随机搜索的状态。这保证了想参与挖矿或者说在工作量证明中获胜的节点唯一的选择就是不断提高自己的算力,而没有任何其它的“捷径”,而这点正是区块链安全性的基石。


挖矿是比特币系统运行的核心环节,但是参与挖矿的节点需要投入大量的资源,包括挖矿设备和电力消耗。显然如果没有激励机制,节点是没有动力去挖矿的。比特币的设计是,节点挖出一个新区块以后,它记录的第一笔交易并不是从全网接收到的交易,而是自己创建的一笔特殊交易——创币交易或者称coinbase交易。假设A节点挖出了一个新区块,它创建的创币交易内容类似于“向A节点的地址支付12.5个比特币”。这12.5个全新的比特币是之前不存在于区块链账本中的增量,也是作为对挖矿节点的奖励。创币交易的特殊在于不消耗UTXO,即没有交易输入只有交易输出。所以给挖出新区块的节点的奖励包括两部分:新币奖励和交易费用。目前矿工获得的主要收益还是新币奖励为主,交易费用占比还比较小。

 

可以看出,挖矿设计的高明之处在于它不仅是一种激励记账的机制,同时解决了加密数字货币新币发行的难题。从2009年1月每个区块奖励50个比特币开始,每四年奖励的比特币数量减少一半(准确地说是210,000个区块),直到2100万比特币全部发行完毕(大约2140年),目前每个新区块奖励12.5个比特币。可以看出,比特币是一种总量有限的紧缩货币。

 

2.6 去中心化共识机制

 

一种货币体系很重要的组成部分就是要有一份所有参与者一致信任的账本。这在传统货币体系中很容易实现,银行作为货币体系的中心结构,保存这样一份账本并在新交易发生时维持对账本的更新。但比特币网络是由分布在互联网上的数以万计的节点组成,并没有中心机构来保存账本,那么那么多节点之间如何形成一份一致认可的账本?中本聪的一个主要创新就在于设计了一种去中心化共识机制,解决了古老的“拜占庭将军难题”,即如何在不可信的环境中在异步节点之间达成共识。共识是网络中数以万计的独立节点遵守了简单的规则,独立异步地交互形成的产物,主要包括以下四个方面:

 

(1)每个节点对接收到的交易的有效性进行独立检验

 

(2)每个节点通过工作量证明算法竞争记账权并对近期的交易独立打包记录到新区块

 

(3)每个节点对接收到的新区块进行独立检验并组装到区块链

 

(4)每个节点独立地选择区块链,在工作量证明机制下选择累计工作量最大的区块链

 

节点对交易数据的独立检验所遵循的规则都是统一规定好的,可能的诈骗、错误等无效交易无法在网络中继续传播。

 

工作量证明算法一方面实现了比特币账本不会被中心节点所控制,另一方面实现区块链历史数据实际不可更改。这两点之前已经介绍过。


每个完全点独立保存并更新区块链。所以当节点从网络接收到一个新区块时,它要检验并决定是否组装到本地的区块链上。检验的内容包括:

 

(1)区块的数据结构语法上有效

 

(2)区块头的哈希值小于目标难度(确认包含足够的工作量证明)

 

(3)第⼀个交易(有且只有第⼀个)是创币交易

 

(4)使用检查清单验证区块内的交易并确保它们的有效性。

 

。。。。。

 

每个节点对每个新区块的独立检验确保了矿工无法欺诈。假设一个欺诈矿工创建一笔交易向自己支付一大笔比特币。接收到这个区块的节点基于相同的检验规则将很快能发现,从而选择拒绝这个新区块,这样这个欺诈矿工不仅不会得到额外的钱,反而会浪费挖矿耗费的大量投入。

 

去中心化共识会遇到的一个情况就是区块链“分叉”。当两个节点几乎同时挖出新区块时。由于互相都没有收到对方的新区块,所以它们会将自己挖出的新区块广播出去。网络上的其它节点就可能在几乎同时接收到两个新区块,而且都可以有效的组装到现有区块链上。这个时候节点会把两个区块都保存下来,形成区块链的两条分叉。“分叉”只是暂时现象,解决办法就是看这两条分叉谁的工作量累计的更快,节点独立地选择累计工作量最大的链作为主链。当所有节点都独立选择最长的链作为区块链主链时,很快全网节点就会重新达成共识。

 

去中心化共识唯一的隐患是可能遭受“共识攻击”,典型的是“51%攻击”。之前介绍过,工作量证明算法使得区块链历史数据实际上不可更改,因为区块的生成需要巨大的工作量,背后需要巨大的算力支撑。但是一旦网络中有超过一半的算力被攻击者掌控,它就可能篡改交易数据。针对记录目标交易的区块,攻击者重新构造一个新区块,并故意与之形成分叉,在新区块中,攻击者可以重新生成一笔与目标交易数额相等但支付地址不同的交易,如果支付地址改为自己掌握的节点地址就可以把这笔钱转给自己。在后续的累计工作量竞赛中,攻击者利用自己掌握的超过一半算力获胜,进而使得故意分叉的链条成为全网的主链,最终实现交易欺诈。所以为了保证大额交易安全,建议在大宗商品交易用比特币支付时,接收方要等到记录此交易的区块深度超过6时,再进行商品交付。

 

比特币:https://peixun.btcmoney.cc/post/8f07f89ddbebc2ac

关键字: btc
免责声明:作为区块链信息平台,本站所提供的资讯信息不代表任何投资暗示,本站所发布文章仅代表个人观点,与比特财经网官方立场无关。投资有风险,入市须谨慎。

2019-2020 Copyright © 比特财经商学院 版权所有