主页 > imtoken官网地址是什么 > 比特币交易流程

比特币交易流程

imtoken官网地址是什么 2023-01-17 07:15:25

比特币交易是比特币系统中最重要的部分。根据比特币系统的设计原则,系统的任何其他部分都旨在确保比特币交易能够在比特币网络中产生、传播和验证,并最终加入比特币交易的全球账本(Bitcoin)。区块链)。比特币交易的本质是包含比特币交易参与者价值转移信息的数据结构。比特币区块链是全球复式账本,每一笔比特币交易都是比特币区块链上的公开记录。

比特币网络中比特币交易的传播

一旦比特币交易被发送到连接到比特币网络的任何节点,该交易将被节点验证。如果交易被验证为有效,该节点会将交易传播到与该节点相连的其他节点;同时,交易发起者会收到一条返回消息,表明交易有效并被接受。如果交易被验证为无效,节点将拒绝接受该交易并向交易发起者返回一条消息,表明该交易被拒绝。

比特币网络是一个点对点网络,这意味着每个比特币节点都连接到其他一些比特币节点(这些其他节点是在点对点协议启动时发现的)。整个比特币网络形成了一个松散连接的“蜘蛛网”,没有固定的拓扑结构或任何结构——这使得所有节点都是平等的。有关比特币交易(包括交易和区块)的信息被传播——从每个节点到它所连接的其他节点。一个刚刚被验证并交付给比特币网络中任何一个节点的交易被发送到三个或四个相邻节点,每个相邻节点将把交易发送给三到四个相邻节点。节点。以此类推,在几秒钟内,一个有效的交易就会像指数级传播波一样在网络中传播,直到所有连接到网络的节点都接收到它。

交易结构

比特币交易是一个具有输入值和输出值的数据结构,该数据结构包含从初始点(输入值)到目标地址的代码信息(输出值)的一笔钱的转移。比特币交易的输入输出值与账户或身份信息无关。它们应该被理解为被特定秘密信息锁定的一定数量的比特币。只有所有者或知道此秘密信息的人才能解锁它。交易的数据结构如下:

事务数据结构中的输入和输出在下面详细描述。

交易输出

交易输出是一个UTXO,一个UTXO主要包括

比特币交易

锁定脚本会将输出锁定在特定的比特币地址,从而将一定数量的比特币的所有权转移给新的所有者。

具体输出结构如下:

您可以使用 blockchain.info API 来查找特定地址的 UTXO:

上述查询中,地址变量的意思是查询与该地址相关的UTXO。在查询结果中,uspent_outputs 对应一个 UTXO 数组。可以看出,这个地址只有一个相关的UTXO。结果中重要字段的含义:

交易输入

假设有一笔交易如下,你需要将0.5BTC从一个地址转移到另一个地址:

比特币交易

# -*- coding:utf-8 -*-
# 使用贪心算法从UTXO列表中选择输出。
from sys import argv
class OutputInfo:
   def __init__(self, tx_hash, tx_index, value):
       self.tx_hash = tx_hash
       self.tx_index = tx_index
       self.value = value
   def __repr__(self):
       return "<%s:%s with %s Satoshis>" % (self.tx_hash, self.tx_index,  self.value)
# 为了发送,从未花费的输出列表中选出最优输出。
# 返回输出列表,并且把其他的改动发送到改变地址。
def select_outputs_greedy(unspent, min_value):
   # 如果是空的话认为是失败了。
   if not unspent: return None
   # 分割成两个列表。
   lessers = [utxo for utxo in unspent if utxo.value < min_value]
   greaters = [utxo for utxo in unspent if utxo.value >= min_value]
   key_func = lambda utxo: utxo.value
   if greaters:
       # 非空。寻找最小的greater。
       min_greater = min(greaters)
       change = min_greater.value - min_value
       return [min_greater], change
   # 没有找到greaters。重新尝试若干更小的。
   # 从大到小排序。我们需要尽可能地使用最小的输入量。
   lessers.sort(key=key_func, reverse=True)
   result = []
   accum = 0
   for utxo in lessers:
       result.append(utxo)
       accum += utxo.value
       if accum >= min_value:
           change = accum - min_value
           return result, "Change: %d Satoshis" % change
   # 没有找到。
   return None, 0
def main():
   unspent = [
       OutputInfo("ebadfaa92f1fd29e2fe296eda702c48bd11ffd52313e986e99ddad9084062167", 1,  8000000),
       OutputInfo("6596fd070679de96e405d52b51b8e1d644029108ec4cbfe451454486796a1ecf", 0, 16050000),
       OutputInfo("b2affea89ff82557c60d635a2a3137b8f88f12ecec85082f7d0a1f82ee203ac4", 0,  10000000),
       OutputInfo("7dbc497969c7475e45d952c4a872e213fb15d45e5cd3473c386a71a1b0c136a1", 0, 25000000),
       OutputInfo("55ea01bd7e9afd3d3ab9790199e777d62a0709cf0725e80a7350fdb22d7b8ec6", 17, 5470541),
       OutputInfo("12b6a7934c1df821945ee9ee3b3326d07ca7a65fd6416ea44ce8c3db0c078c64", 0, 10000000),
       OutputInfo("7f42eda67921ee92eae5f79bd37c68c9cb859b899ce70dba68c48338857b7818", 0, 16100000),
   ]
   if len(argv) > 1:
       target = long(argv[1])
   else:
       target = 55000000
   print "For transaction amount %d Satoshis (%f bitcoin) use: " % (target, target/ 10.0**8)
   print select_outputs_greedy(unspent, target)
if __name__ == "__main__":
   main()

上面的代码模拟了一个比特币地址对应的UTXO列表,target表示要输出的比特币的大小,select_outputs_greedy方法使用贪心算法从这个列表中获取目标大小的比特币。

运行这段代码的结果是:

([<7dbc497969c7475e45d952c4a872e213fb15d45e5cd3473c386a71a1b0c136a1:0 with 25000000 Satoshis>, 
<7f42eda67921ee92eae5f79bd37c68c9cb859b899ce70dba68c48338857b7818:0 with 16100000 Satoshis>, 
<6596fd070679de96e405d52b51b8e1d644029108ec4cbfe451454486796a1ecf:0 with 16050000 Satoshis>],
'Change: 2150000 Satoshis') 

输出集包含三个UTXO,总价值为0.5715BTC,而我们的目标是0.55BTC,所以输出也有一个Change:0.0215BTC,表示改变.

当这个模拟交易完成后,从数据库中删除输出中的三个UTXO比特币交易,并生成两个新的UTXO:一个是目标大小的0.55BTC,另一个是寻找Zero的0.0215BTC。因此,在整个交易中,未花费中满足条件的三个 UTXO 构成了三个交易输入,target 和 Change size 的 UTXO 构成了两个交易输出。

在上例的交易中选择了三个 UTXO。一旦选择了一个 UTXO,钱包将为每个 UTXO 生成一个解锁脚本。此解锁脚本还包括:

选中 UTXO 加上解锁脚本构成交易输入。交易输入的具体数据结构如下:

比特币交易

从结构可以看出,一个交易的输入包括:

解锁脚本和锁定脚本

比特币的交易验证引擎依赖于两种类型的脚本来验证比特币交易:锁定脚本和解锁脚本。

每个比特币客户端都通过执行锁定和解锁脚本来验证交易。对于比特币交易中的每个输入,验证软件首先检索输入指向的 UTXO。这个 UTXO 包含一个定义支出条件的锁定脚本。接下来,验证软件会读取输入中包含的解锁脚本,尝试使用此 UTXO,并执行这两个脚本。

在以前的比特币客户端中,解锁和锁定脚本存在于链中并按顺序执行。出于安全考虑,比特币开发者在 2010 年修改了这一功能,因为存在“允许异常解锁脚本将数据推送到堆栈并污染锁定脚本”的漏洞。在当今的比特币世界中,这两个脚本在堆栈通过时分别执行。

比特币交易脚本语言是一种基于反向波兰表示法的基于堆栈的执行语言。主要有以下操作:

OP_DUP的操作是把栈顶的数据拷贝一份,放到栈顶

比特币交易

从栈顶弹出两个数据,比较是否相等。如果为真,将执行下一个堆栈操作。如果为假,整个验证过程都会失败

p>

OP_HASH160 从栈顶弹出数据,进行哈希运算,然后将结果压入栈

OP_CHECKSIG 从栈顶弹出两个数据,比较,结果压入栈

具体规则如下:

锁定脚本

OP_DUP OP_HASH160 OP_EQUALVERIFY OP_CHECKSIG

比特币交易

可以看出,整个锁脚本中唯一的变量就是发送者公钥哈希

解锁脚本

交易验证

运行解锁脚本 + 锁定脚本 => TRUE

交易验证

比特币网络接收到交易输入后,会对交易进行验证,验证通过后,会产生交易输出。在交易输入中,UTXO属于发送方,在交易输出中,UTXO属于接收方。

栈结构的主要操作规则有:

那么,比特币交易验证流程如下:

验证通过后,会产生相应的交易输出比特币交易,将比特币从一个所有者转移到另一个所有者。