ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

《区块链编程》第十一章

2022-01-16 12:01:40  阅读:256  来源: 互联网

标签:None parent level 第十一章 编程 merkle hashes 区块 root


文章目录

《区块链编程》第十一章

简单支付验证

练习1

p180

代码实现

# -*- coding: utf-8 -*-
# @Author: 从化北(喵星人)
# @Date:   2022-01-16 10:43:44
# @Last Modified by:   从化北
# @Last Modified time: 2022-01-16 11:00:29
from helper import hash256


def merkle_parent(hash1, hash2):
    '''Takes the binary hashes and calculates the hash256'''
    return hash256(hash1 + hash2)


hash0 = bytes.fromhex('c117ea8ec828342f4dfb0ad6bd140e03a50720ece40169ee38b\
dc15d9eb64cf5')
hash1 = bytes.fromhex('c131474164b412e3406696da1ee20ab0fc9bf41c8f05fa8ceea\
7a08d672d7cc5')
print(merkle_parent(hash0, hash1).hex())

测试

8b30c5ba100f6f2e5ad1e2a742e5020491240f8eb514fe97c713c31718ad7ecd
[Finished in 318ms]

练习2

p181

代码实现

# -*- coding: utf-8 -*-
# @Author: 从化北(喵星人)
# @Date:   2022-01-16 10:53:22
# @Last Modified by:   从化北
# @Last Modified time: 2022-01-16 11:06:46

from helper import merkle_parent


def merkel_parent_level(hashes):
    '''Takes a list of binary hashes and returns a list that's half
    the length'''
    if len(hashes) == 1:
        raise RuntimeError('Cannot take a parent level with only 1 item')
    if len(hashes) % 2 == 1:
        hashes.append(hashes[-1])
    parent_level = []
    for i in range(0, len(hashes), 2):
        parent = merkle_parent(hashes[i], hashes[i + 1])
        parent_level.append(parent)
    return parent_level


hex_hashes = [
    'c117ea8ec828342f4dfb0ad6bd140e03a50720ece40169ee38bdc15d9eb64cf5',
    'c131474164b412e3406696da1ee20ab0fc9bf41c8f05fa8ceea7a08d672d7cc5',
    'f391da6ecfeed1814efae39e7fcb3838ae0b02c02ae7d0a5848a66947c0727b0',
    '3d238a92a94532b946c90e19c49351c763696cff3db400485b813aecb8a13181',
    '10092f2633be5f3ce349bf9ddbde36caa3dd10dfa0ec8106bce23acbff637dae',
]
hashes = [bytes.fromhex(h) for h in hex_hashes]
level = merkel_parent_level(hashes)
for h in level:
    print(h.hex())

测试

8b30c5ba100f6f2e5ad1e2a742e5020491240f8eb514fe97c713c31718ad7ecd
7f4e6f9e224e20fda0ae4c44114237f97cd35aca38d83081c9bfd41feb907800
3ecf6115380c77e8aae56660f5634982ee897351ba906a6837d15ebc3a225df0
[Finished in 323ms]

练习3

p182

代码实现

# -*- coding: utf-8 -*-
# @Author: 从化北(喵星人)
# @Date:   2022-01-16 11:07:52
# @Last Modified by:   从化北
# @Last Modified time: 2022-01-16 11:14:24
from helper import merkle_parent_level


def merkle_root(hashes):
    '''Takes a list of binary hashes and returns the merkle root
    '''
    # current level starts as hashes
    current_level = hashes
    # loop until there's exactly 1 element
    while len(current_level) > 1:
        # current level becomes the merkle parent level
        current_level = merkle_parent_level(current_level)
    # return the 1st item of the current level
    return current_level[0]


hex_hashes = [
    'c117ea8ec828342f4dfb0ad6bd140e03a50720ece40169ee38bdc15d9eb64cf5',
    'c131474164b412e3406696da1ee20ab0fc9bf41c8f05fa8ceea7a08d672d7cc5',
    'f391da6ecfeed1814efae39e7fcb3838ae0b02c02ae7d0a5848a66947c0727b0',
    '3d238a92a94532b946c90e19c49351c763696cff3db400485b813aecb8a13181',
    '10092f2633be5f3ce349bf9ddbde36caa3dd10dfa0ec8106bce23acbff637dae',
    '7d37b3d54fa6a64869084bfd2e831309118b9e833610e6228adacdbd1b4ba161',
    '8118a77e542892fe15ae3fc771a4abfd2f5d5d5997544c3487ac36b5c85170fc',
    'dff6879848c2c9b62fe652720b8df5272093acfaa45a43cdb3696fe2466a3877',
    'b825c0745f46ac58f7d3759e6dc535a1fec7820377f24d4c2c6ad2cc55c0cb59',
    '95513952a04bd8992721e9b7e2937f1c04ba31e0469fbe615a78197f68f52b7c',
    '2e6d722e5e4dbdf2447ddecc9f7dabb8e299bae921c99ad5b0184cd9eb8e5908',
    'b13a750047bc0bdceb2473e5fe488c2596d7a7124b4e716fdd29b046ef99bbf0',
]
hashes = [bytes.fromhex(x) for x in hex_hashes]
root = merkle_root(hashes)
print(root.hex())

        

测试

acbcab8bcc1af95d8d563b77d24c3d19b18f1486383d75a5085c4e86c86beed6
[Finished in 399ms]

练习4

p183

代码实现

# -*- coding: utf-8 -*-
# @Author: 从化北(喵星人)
# @Date:   2022-01-16 11:20:26
# @Last Modified by:   从化北
# @Last Modified time: 2022-01-16 11:20:26
class Block:
...
    def validate_merkle_root(self):
        '''Gets the merkle root of the tx_hashes and checks that it's
        the same as the merkle root of this block.
        '''
        # reverse each item in self.tx_hashes
        hashes = [h[::-1] for h in self.tx_hashes]
        # compute the Merkle Root and reverse
        root = merkle_root(hashes)
        # return whether self.merkle_root is the same
        return root[::-1] == self.merkle_root

运行结果

练习5

p187

代码实现

# -*- coding: utf-8 -*-
# @Author: 从化北(喵星人)
# @Date:   2022-01-16 11:24:09
# @Last Modified by:   从化北
# @Last Modified time: 2022-01-16 11:26:48
import math
total = 27
max_depth = math.ceil(math.log(total, 2))
merkle_tree = []
for depth in range(max_depth + 1):
    num_itmes = math.ceil(total / 2 ** (max_depth - depth))
    level_hashes = [None] * num_itmes
    merkle_tree.append(level_hashes)
for level in merkle_tree:
    print(level)


运行结果

[None]
[None, None]
[None, None, None, None]
[None, None, None, None, None, None, None]
[None, None, None, None, None, None, None, None, None, None, None, None, None, None]
[None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None, None]
[Finished in 397ms]

练习6

p193

代码实现

# -*- coding: utf-8 -*-
# @Author: 从化北(喵星人)
# @Date:   2022-01-16 11:38:42
# @Last Modified by:   从化北
# @Last Modified time: 2022-01-16 11:39:00


class MerkleTree:
...
    @classmethod
    def parse(cls, s):
        '''Takes a byte stream and parses a merkle block. Returns a Merkle Block object'''
        # version - 4 bytes, Little-Endian integer
        version = little_endian_to_int(s.read(4))
        # prev_block - 32 bytes, Little-Endian (use [::-1])
        prev_block = s.read(32)[::-1]
        # merkle_root - 32 bytes, Little-Endian (use [::-1])
        merkle_root = s.read(32)[::-1]
        # timestamp - 4 bytes, Little-Endian integer
        timestamp = little_endian_to_int(s.read(4))
        # bits - 4 bytes
        bits = s.read(4)
        # nonce - 4 bytes
        nonce = s.read(4)
        # total transactions in block - 4 bytes, Little-Endian integer
        total = little_endian_to_int(s.read(4))
        # number of transaction hashes - varint
        num_hashes = read_varint(s)
        hashes = []
        # each transaction is 32 bytes, Little-Endian
        for _ in range(num_hashes):
            hashes.append(s.read(32)[::-1])
        # length of flags field - varint
        flags_length = read_varint(s)
        # read the flags field
        flags = s.read(flags_length)
        # initialize class
        return cls(version, prev_block, merkle_root, timestamp, bits, nonce, total, hashes, flags)

运行结果

练习7

p197

代码实现

# -*- coding: utf-8 -*-
# @Author: 从化北(喵星人)
# @Date:   2022-01-16 11:45:26
# @Last Modified by:   从化北
# @Last Modified time: 2022-01-16 11:45:26

class MerkleBlock:
    ...
    def is_valid(self):
        '''Verifies whether the merkle tree information validates to the merkle root'''
        # convert the flags field to a bit field
        flag_bits = bytes_to_bit_field(self.flags)
        # reverse self.hashes for the merkle root calculation
        hashes = [h[::-1] for h in self.hashes]
        # initialize the merkle tree
        merkle_tree = MerkleTree(self.total)
        # populate the tree with flag bits and hashes
        merkle_tree.populate_tree(flag_bits, hashes)
        # check if the computed root reversed is the same as the merkle root
        return merkle_tree.root()[::-1] == self.merkle_root

运行结果

标签:None,parent,level,第十一章,编程,merkle,hashes,区块,root
来源: https://blog.csdn.net/qq_42182429/article/details/122520339

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有