比特币是怎么生成的?

作者:拿铁大
链接:http://www.zhihu.com/question/20586821/answer/16678130
来源:知乎
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

block的版本 version
上一个block的hash值: prev_hash
需要写入的交易记录的hash树的值: merkle_root
更新时间: ntime
当前难度: nbits

挖矿的过程就是找到x使得
SHA256(SHA256(version + prev_hash + merkle_root + ntime + nbits + x )) < TARGET

上式的x的范围是0~2^32, TARGET可以根据当前难度求出的。除了x之外,你还可以尝试改动merkle_root和ntime。由于hash的特性,找这样一个x只能暴力搜索。

一旦你找到了x,你就可以广播一个新的block,其他客户端会验证你的block是否合法。如果你的block被接受,由于每个block中的第一笔交易必须是将新产生25个比特币发送到某个地址,当然你会把这个地址设为你所拥有的地址来得到这25个比特币。

—————————————————————

比特币从开始到现在的每一笔交易记录都保存在网络上,整个比特币网络维护的一个巨大的交易记录文件(现在大约12G)。 这个文件的更新周期平均是10分钟,新加入的交易记录叫做一个block,而这个硕大的文件由一串block组成,叫做block chain.

为什么是25个比特币?
这是规定。最初是50个比特币,每产生剩下比特币的一半,这个所得就会减半,这样最终能产生的比特币总量趋近于2100万。如果你现在仍然声称挖到了50个比特币,这是不会被其他客户端接受的,这个block就算白挖了。

怎么保证更新周期平均是10分钟?
TARGET越小,解出x的难度就越大,每产生2016个block(约14天),网络会根据这段时间产生新block的平均间隔调整之后的TARGET。

是不是计算速度最快的人总是先解出来?
不是。你总是想把挖矿所得据为己有,所以每个人在计算时,发送挖矿所得的地址是不一样的,这样merkle_root就不同,也就是说每个人是从不同的初始状态开始求解的。

同时解出来怎么办?
block chain会出现分叉,部分客户端接受了A,部分接受了B,直到某个分支变得更长,所有人就会选择这个更长的分支。如果你挖出来的不幸没有被选中,你的挖矿所得就无效了。

既然选更长的分支,那我用很低的难度去求解怎么办?
客户端在众多分支中找到符合当前难度且最长的。

这些计算浪费了吗?
如果你要把一笔钱花两次,你需要这么做。挖到一个新的block,但是藏着不广播,并继续挖矿。找到商家A,支付比特币,让网络上的其他人挖到block并写入这笔交易记录。找到商家B,支付比特币,写入自己挖的block。如果你能抢先挖到两个block并广播出去,所有人会以你这个更长的分支为当前的block chain,商家A收到的比特币就不被承认了。这样攻击成功的概率取决于你计算hash的速度。整个网络的计算力足够高的话,这样的攻击或者成功率极低,或者成本极大。
shawn
看着够晕的
3 年前
拿铁大(作者) 回复 shawn
哪部分晕啊,我写得比较烂
3 年前
张帆
1.
“是不是计算速度最快的人总是先解出来?
不是。你总是想把挖矿所得据为己有,所以每个人在计算时,发送挖矿所得的地址是不一样的,这样merkle_root就不同,也就是说每个人是从不同的初始状态开始求解的。”
求解只能是暴力的话,假定有三个人挖矿,那计算速度最快的人总是先解出来一个X(X1),花了1分钟;然后第二快的人也解出了他的X(X2),花了2分钟;最慢的人最后解出了他的X(X3),花了3分钟,那这三个X是抽奖呢还是最小的获胜?

2.
每产生2016个block(约14天), 会调整难度,如果现在挖矿的人很多,难度很大,会使得计算能力小的个体户在10分钟之内解不出X?那矿池中的节点是怎么合作工作的?
3 年前
拿铁大(作者) 回复 张帆
x1,x2,x2各自抽奖拼人品 矿池给用户的一般是难度为1的任务,只需要2^32,大于7M/s就能在10分钟内完成。如果在你未解出来时网络有新的区块产生,就要重新开始,矿池会检查你提交的是否为已经迟了。
3 年前
拿铁大(作者) 回复 张帆
最快的人赢。但是赢的概率取决于你的计算力
3 年前
张帆 回复 拿铁大(作者)
1。你前一个回复不是说抽奖拼人品么,怎么这儿说最快的赢,是看到新资料了?如果说抽奖,哪个节点来主持这个抽奖? 2。矿池中每个矿工是解自己的那个x,还是帮别人解x?如果是前者那难度是p2p系统定的,你说的难度为1如何理解
3 年前
拿铁大(作者) 回复 张帆
不好意思,之前手机打字。
1. 那计算速度最快的人总是先解出来一个X(X1),花了1分钟;然后第二快的人也解出了他的X(X2),花了2分钟;最慢的人最后解出了他的X(X3),花了3分钟

你的理解不对,不是计算速度最快的人总能赢,只是概率更高,因为大家从不同的状态开始穷举。我说的最快是指最早解出的,抱歉有歧义了。

抽奖只是一个比方,只要你找的解使得你的hash值小于target,你就会赶紧广播出去,其他人也很容易验证,只要计算一下hash就可以了,并不需要人来主持。

2. 矿池是大致是这样工作的,我会稍后补完。
所谓难度是最大target与当前target的比值,最大target即0x00000000FFFFFFF…….,也就是这里说的难度1,假设hash函数分布均匀的话,找到满足难度1的概率为1/(2^32)。
矿池让你求解难度为1的工作,在从矿工们提交的结果中找有没有满足小于当前target的,有的话矿池就挖到了比特币,然后根据不同的方法分配给矿工。
当然矿池也可以分配给你任意难度的工作,减少矿工和矿池间的网络交互。
3 年前
张帆
多谢回答!
那你是说,解的快慢跟两个因素有关,a)他的题的解是不是正好在搜索空间的前面,b)他的计算能力。
1。那在目前上万的节点情况下,如果x1与x2在同一秒解出来并广播的话,一群节点确认x1是对的,另一群节点确认x2是对的,那x1,x2到底谁能得到25个币,没有人主持的话,如何确保系统的稳定?
2。如何保证10分钟左右产生25个币?x1如果花了一分钟解出来,并得到了其他节点的确认,那剩下的9分钟是继续解题还是等待这个10分钟block结束?
3 年前
拿铁大(作者)
如何穷举是随意的,可以从0开始,也可以从2^32开始,归根结底就是看计算能力。

1. 网络会暂时分裂,一部分人以A分支继续挖,另一部分人以B分支继续挖,取决于他们先看到哪个区块。这样直到某个分支的长度大于另一个分支,网络就会以这条更长的分支为准,通常只要看下一个区块就决出胜负了。假如A分支先产生了下一个区块,那么所有人就以A这条分支挖下一个区块,B分支上的区块就不被承认了。

2. 回答里有关于10分钟的解答。不是保证每10分钟产生一个区块,而是在一段时间内平均10分钟产生一个区块。比特币网络每2016个区块就会调整计算难度,使得平均间隔趋近于10分钟。
因此不存在剩下9分钟这个概念,而是大家已经开始挖下一个区块了。
3 年前
张帆
多谢回答!
1。交易的数据如何保证完整和不冲突呢,如果A分支有一个甲付给乙的交易,
B分支有一个甲付给丙的交易,甲的帐号假如有足够的钱,如何合并这些交易数据,甲的帐号假如没有足够的钱,如何确定哪个交易是非法的?
2。矿池中每个矿工是解自己的那个x,还是大家在合作解同一道题的x?这个我还不太清楚。
3。如果是大家在合作解同一道题的话,是不是需要根据各个矿工不同的计算能力来分配搜索空间大小?
3 年前
拿铁大(作者)
1. 如果甲的余额足够,比特币客户端会自动继续转发另一个交易。比如你在A分支,你看到的是甲给乙的交易已经写入区块链,你会继续广播甲给丙的交易,反之亦然。如果余额不足,交易就会非法,不会被写入区块链中。随着A,B分支分出胜负,这两笔交易只是在写入顺序会不同。

2. 部分矿池是一起解矿池管理者的x,因为是他获取比特币再分发。 现在有很多新的方式,可以让用户解自己的x。总之矿池要保证你不能把挖到的钱全吞了,而是用一定规则分发给参与的用户。

3. 不同矿池分发任务的机制不一样。最简单的机制是给每个用户发送难度为1的任务,用户解出来后接着发送下一个任务,计算能力强解的任务自然就多。
3 年前
coin bit
楼主研究过源代码吗?大家切磋切磋。
3 年前
王少奇 回复 拿铁大(作者)
能否解答下,比特币是谁产生的,最终支付给拥有比特币者的人是谁?
3 年前
拿铁大(作者) 回复 王少奇
每次找到符合当前难度解的人获得新产生的比特币, 这些新产生的比特币直接记录在他所拥有的地址了, 即某A获得25比特币+当前区块剩余交易的手续费,来源是新产生, 不需要第三方来支付给他. 比如Bitcoin Block #241223 这个区块的第一笔交易 Bitcoin Transaction 7cbc2187ddd6d6e9d253977b5881a5210e302f33f283f6f16d913eb2ecb39e75. 每一个新产生的区块里的第一笔交易都是类似的. 为什么能这么做是大家接受并拥护比特币网络的设定.
3 年前
文刀
疑问:
都说全球产矿机的只有几家公司,芯片很少,是因为写芯片技术难度超高?不是说算法开源吗,号称其中一家是中国的ASICME,但目前一台机都还没有出过,都是付款了等机,机又在等芯片,芯片在南瓜张,结果查半天也查不到这人姓谁名啥,长啥样,这感觉太玄乎了,和比特币本身的感觉一样。。。。
后面大家都用矿机,运算速度加快许多,不是一下就挖完了?
3 年前
拿铁大(作者) 回复 文刀
算法开源不意味着芯片容易做,到了定制芯片这一级别,要考虑功耗,散热等一堆问题,流片一次一般就要等上一个月,封装又是大半个月,也就是说存在设计和生产周期问题。南瓜张他们的主要瓶颈就是产能了,所以让人感觉这么玄乎。
前面有提到,比特币系统的难度会自动调整,所以突然提高运算速度能爽几天,但很快难度就会提高,挖的速度又会下降。
3 年前
hua xue
请问构成参数的merkle_root + ntime + nbits都是实时变量吗?比如a得到了满足标准的x,它会把所有参数广播给别人验证吗?
第二,要实现所有的节点同步几乎是不可能的,按照最长链的标准,那挖完矿10分钟后被其他链取代的例子不是会很多吗?10分钟内被兑现了怎么办?
3 年前
拿铁大(作者) 回复 hua xue
merkle_root是包括当前待写入的交易以及你获得25比特币这笔交易(coinbase)的Hash树的根Hash,是实时的(挖矿时需要修改coinbase)。ntime是当前时间,nbits是当前难度,这个是每2016个区块调整一次的。你广播出去的是你生成的区块,包含所有这些信息。

会被取代,例子可以看这里Orphaned Blocks ,因此存在限制,要求挖矿所得的比特币在120个新区块产生后才能使用。
3 年前
chen swemp
写的不错。看来是业内人士,我转载了。
3 年前
南方
写的好专业,不明觉厉!请教楼主如果两笔交易冲突了,网络如何判断谁胜出呢?我查了一下,wiki里说Bitcoin protects against double spending by verifying each transaction added to the block chain to ensure that the inputs for the transaction had not previously already been spent. 这里好像说的是在先的交易胜出,不过按你的意思好像是分支更长的交易胜出。怎么理解这个问题呢?另外请教楼主怎么看BTC Garden和烤猫各自的芯片项目:)
3 年前
拿铁大(作者) 回复 南方
这里的意思是会检查交易的输入是否已经被花掉了,即包含这个输入的交易是否已经被写入了block chain或者是否同时收到几个交易有相同的输入。前一种情形,这里的先后已经有了,即被写入的在先;对于第二种情形,这个客户端接收到是有先后。后来的会被视为企图double spend,不会被继续转发。 但是一旦客户端发现有更长的分支,就要重新去看这些交易,那么可能之前被你视为double spend的交易在另一个分支被写入了,而原来被写入的反而是double spend了。

这些项目去看看http://cnbitcointalk.com/
3 年前
负负得正
刚接触比特币,想问楼主一些比较初级的问题,所有的交易记录存放在哪里怎么被查询用来判断新的block的
3 年前
拿铁大(作者) 回复 负负得正
每个运行BitCoin-Qt客户端的机器上都有所有交易记录,即block chain,新block是从客户端之间的P2P网络接收到的。
3 年前
负负得正
那么整个block chain会不会很大,如果要挖矿,需要下载这些数据吗
3 年前
拿铁大(作者) 回复 负负得正
快10多GB了吧,挖矿不需要,你去了解下怎么连矿池吧。
3 年前
萝卜甲
“比特币从开始到现在的每一笔交易记录都保存在网络上,整个比特币网络维护的一个巨大的交易记录文件(现在大约12G)。”

这玩儿是死局啊,随着用户交易量增长,这个数据会越来越大,到后面会大到无法使用。
3 年前
面壁者与破壁者 回复 萝卜甲
这个中本聪会考虑到,所以设计了一个不需要每台电脑都安装交易历史文件的方法就是防伪码。而完整的交易记录只会安装在部分电脑上,其他电脑采用防伪码来验证。这样就解决了这个问题。当然,现在才十几个G,也还好。
3 年前
魏巍
不明觉厉,
3 年前
侯文
不是很懂啊 那比特币 有投资购买的必要么?
3 年前
黄凯旋
我想问个比较困扰我的问题:
比特币挖矿难度每隔2016个块自动调节,确保10分钟产生一个块,这个调节算法是怎样的?
貌似要用最近区块时间来计算,那就有了第二个问题。每个块的时间戳都是旷工自己写的,全网如何保证区块时间戳是可信的?如果我故意将时间戳写的很晚,那就可以拉长区块产生时间欺骗网络调低挖矿难度。
5 月前
上一页12下一页
更多回答
26
王滨 ,Python, http://thbattle.net
比特币的所有交易都是存储在block里的。每一个block大概包含这些信息:前一个block的hash一堆transaction(交易信息)一个无意义的值,用来保证block的hash满足“比某个特定值小”的这个性质。按照规则,你可以凭空的在block里加一条transaction,没有来源… 显示全部
10
nareix
云风的这篇文章讲得挺清楚的:http://blog.codingnow.com/2011/05/bitcoin.html