使用go语言构建区块链 Part1.基础原型

这篇具有很好参考价值的文章主要介绍了使用go语言构建区块链 Part1.基础原型。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

英文源地址

简介

区块链技术是21世纪最具变革型的技术之一,它仍处于成长阶段, 其潜力尚未完全实现.从本质上说, 区块链是一个分布式的记账数据库.但它的独特之处在于它不是一个私有数据库,而是一个公共数据库, 也就是说, 每个使用它的人都有它的完整或部分副本.而且,只有在征得其他数据库维护者的同意的情况下, 才能添加新记录.此外, 正是区块链使加密货币和智能合约成为可能.
在本系列文章中, 我们将构建一个基于简单区块链实现的简易的数字加密货币.

Block区块

让我们从’区块链’的区块部分开始. 在区块链中, 它是存储有价值信息的块.例如, 比特币区块存储交易, 这是任何加密货币的本质. 除此之外, 一个块还包含一些技术信息, 比如它的版本, 当前时间戳和前一个块的哈希值.
在本文中, 我们不打算实现区块链或比特币规范中描述的区块, 相反, 我们将使用它的简化版本, 其中只包含重要信息.它看起来是这样的.

type Block struct {
	Timestamp int64
	Data []byte
	PrevBlockHash []byte
	Hash []byte
}

Timestamp是当前时间戳(区块创建的时间), Data时区块中包含的实际有价值的信息, PrevBlockHash存储前一个区块的哈希值, Hash是当前区块的哈希值.在比特币规范中, Timestamp, PrevBlockHash和Hash是区块头部, 它们形成一个独立的数据结构, 而transactions(我们例子中的Data)是一个独立的数据结构.为了简单起见, 我们把它们放在一起.
那么我们如何计算哈希呢?哈希值的计算方式是区块链非常重要的特征, 正式这个特点使得区块链安全.问题是计算哈希是一项计算密集型操作, 即使在高速计算机上也需要耗费一些时间(这就是为什么人们购买强大的GPU来挖矿比特币). 这是一个有意义的设计, 这使得添加新区块变得困难, 从而阻止了它们在添加后被修改.我们将在以后的文章中讨论并实现该机制.
现在, 我们将获取区块字段, 将它们连接起来, 并在连接的组合上计算SHA-256哈希值.让我们在SetHash方法中实现这一点:

func (b *Block) SetHash() {
	timestamp := []byte(strconv.FormatInt(b.Timestamp, 10))
	header := bytes.Join([][]byte{b.PrevBlockHash, b.Data, timestamp}, []byte{})
	hash := sha256.Sum256(headers)
	b.Hash = hash[:]
}

接下来, 遵循Golang的约定, 我们将实现一个简化区块创建的函数:

func NewBlock(data string, prevBlockHash []byte) *Block {
	block := &Block{time.Now().Unix(), []byte(data), prevBlockHash, []byte{}}
	block.SetHash()
	return block
}

这就是整个区块!

区块链

现在让我们实现一个区块链. 从本质上讲, 区块链只是一个具有一定结构的数据库: 它是一个有序的反向链表. 这意味着数据块是按插入顺序存储的, 并且每个数据块都链接到前一个数据块.这种结构允许快速获取链中的最新区块, 并(有效地)通过其散列值获取区块.
在Golang中, 这种结构可以通过使用数组和字典来实现.数组保持有序地哈希值(在Go中数组是有序的), 而字典将保持哈希值->区块对(字典是无序的). 但是对于我们的区块链原型, 我们将只使用一个数组, 因为我们现在不需要通过它们的哈希值来获取区块.

type Blockchain struct {
	blocks []*Block
}

这是我们的第一个区块链!我从没想过会这么容易😉
现在让我们向它添加区块:

func (bc *Blockchain) AddBlock(data string) {
	prevBlock := bc.blocks[len(bc.blocks)-1]
	newBlock := NewBlock(data, prevBlock.Hash)
	bc.blocks = append(bc.blocks, newBlock)
}

就是这样了吗?
要添加一个新区块, 我们需要一个现有的区块, 但是我们的区块链中没有区块!因此, 在任何区块链中, 必须至少有一个区块, 而这样的区块, 即链的第一个区块, 被称为创世区块(gensis block).让我们实现一个创建这样一个区块的方法.

func NewGenesisBlock() *Block {
	return NewBlock("Genesis Block", []byte{})
}

现在, 我们可以实现一个用创世区块创建区块链的函数:

func NewBlockchain() *Blockchain {
	return &Blockchain{[]*Block{NewGenesisBlock()}}
}

让我们检查下区块链是否正常工作:

func main() {
	bc := NewBlockchain()

	bc.AddBlock("Send 1 BTC to Ivan")
	bc.AddBlock("Send 2 more BTC to Ivan")

	for _, block := range bc.blocks {
		fmt.Printf("Prev. hash: %x\n", block.PrevBlockHash)
		fmt.Printf("Data: %s\n", block.Data)
		fmt.Printf("Hash: %x\n", block.Hash)
		fmt.Println()
	}
}

输出结果

Prev. hash:
Data: Genesis Block
Hash: fc5e6a0666636c732f11b6d159081d0838ad126026ffef5d98b9a0a8cbf2f21e

Prev. hash: fc5e6a0666636c732f11b6d159081d0838ad126026ffef5d98b9a0a8cbf2f21e
Data: Send 1 BTC to Ivan
Hash: 4028898ea2a9907266de11ad1a770fb78163c05bb7b7a3d712ee59ea1473253e

Prev. hash: 4028898ea2a9907266de11ad1a770fb78163c05bb7b7a3d712ee59ea1473253e
Data: Send 2 more BTC to Ivan
Hash: 5571f6b8ad167ad209b1effe129dc139934d7487999am85bf081e83116c12a5

就是这样!

总结

我们构建了一个简易的区块链原型: 它只是一个区块数组, 每个区块都于前一个区块有链接.然而, 实际的区块链要复杂的多.在我们的区块链中添加新区块是简单而快速的, 但在真正的区块链中添加新区块需要一些工作: 在获得添加新区块的许可之前, 必须执行一些繁重的计算任务(这种机制成为工作量证明).此外, 区块链是一个分布式数据库, 没有单一的决策者.因此, 一个新的区块必须得到网络中其他参与者的确认和批准(这种机制成为共识consensus).我们的区块链中还没有事务.
在以后的文章中, 我们将介绍这些特性.

Links:

Full source codes: https://github.com/Jeiwan/blockchain_go/tree/part_1
Block hashing algorithm: https://en.bitcoin.it/wiki/Block_hashing_algorithm文章来源地址https://www.toymoban.com/news/detail-469836.html

到了这里,关于使用go语言构建区块链 Part1.基础原型的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 第二章:CSS基础进阶-part1:CSS高级选择器

    后代选择器:E F 子元素选择器: EF 相邻兄弟选择器:E+F 群组选择器:多个选择器以逗号隔开(selector1,selector2,…) 属性选择器:E[attr],E[attr=“value”], E[attr~=“value”] CSS 属性选择器通过已经存在的属性名或属性值匹配元素 伪类选择器(简称:伪类)通过冒号来定义,它定义了

    2024年02月13日
    浏览(25)
  • 【头歌educoder】离散数学实训参考-第二章-关系-part1-关系基础

    目录  第一关:求给定集合的对角线关系(Diagonal Relation)  第二关:关系的合成  第三关:关系的幂运算  第四关:关系的并运算  第五关:转换成关系矩阵  第六关:自反关系的判断  第七关:反自反关系的判断  第八关:对称关系的判断  第九关:非对称关系的判断  第十

    2024年02月07日
    浏览(26)
  • python文件处理之open()功能的使用part1

    什么是文件? 文件是操作系统提供给用户或者是应用程序用于操作硬盘的虚拟概念或者说接口。 为什么要有文件? 用户通过应用程序可以通过文件,将数据永久保存到硬盘中。 详细的说:用户和应用程序操作的是文件,对文件的所有操作,都是向操作系统发送系统调用,然

    2023年04月08日
    浏览(40)
  • 飞行动力学 - 第4节-part1-螺旋桨式飞机的最大最小速度 之 基础点摘要

    最小功率:类似抛物线底部斜率为零的位置 最大速度:所需功率与输出功率交点位置 最小速度:所需功率与输出功率交点位置 根据前面功率与速度曲线进行求导,当斜率为零时即功率最小。 课程中通过手工推导过程,讲述了最小功率的解析解求解方式。 关于所需功率和输

    2024年02月12日
    浏览(73)
  • 飞行动力学 - 第5节-part1-爬升性能、螺旋桨式飞机的爬升性能 之 基础点摘要

    爬升率:爬升时的垂直速度 爬升角:爬升时与水平的夹角 其中爬升率定义: R / C = Δ P W = P A − P R W R/C = frac {varDelta P} {W} = frac {P_A - P_R} {W} R / C = W Δ P ​ = W P A ​ − P R ​ ​ 螺旋桨飞机 P A P_A P A ​ 在给定高度为常量 飞机重量W为常量 当 P R P_R P R ​ 未最小值时,爬升率为

    2024年02月12日
    浏览(30)
  • 动态规划(一) part1

    T1:一个数组 中的最长 升序 子序列 的长度 给你一个整数数组  nums  ,找到其中最长严格递增子序列的长度。 子序列  是由数组派生而来的序列,删除(或不删除)数组中的元素而不改变其余元素的顺序。例如, [3,6,2,7]  是数组  [0,3,1,6,2,2,7]  的子序列。 解: 1.关键 (1)

    2023年04月19日
    浏览(69)
  • Redis项目 PART1

    第一部分:含注册登入+商户查询(使用缓存) 使用redis而不用传统的session的原因(session共享问题):每个tomcat中都有一份属于自己的session,假设用户第一次访问第一台tomcat,并且把自己的信息存放到第一台服务器的session中,但是第二次这个用户访问到了第二台tomcat,那么在第

    2024年02月16日
    浏览(30)
  • 计算机网络 Part1

    目录 计算机网络的一些术语: 计算机网络的重点: 整体结构以及HTTP部分一些问题: TCP以及UDP相关的问题: DNS以及网络安全相关的问题: 1. OSI七层模型的每一层分别是什么?对应的协议有哪些? 传输层协议和网络层协议有什么区别?   HTTP协议为什么设计为无状态的? H

    2024年02月12日
    浏览(28)
  • SwiftUI 布局协议 - Part1

    今年 SwiftUI 新增最好的功能之一必须是布局协议。它不但让我们参与到布局过程中,而且也给了我们一个很好的机会去更好的理解布局在 SwiftUI 中的作用。 早在2019年,我写了一篇文章 SwiftUI 中 frame 的表现 ,其中,我阐述了父视图和子视图如何协调形成最终视图效果。那里描

    2024年02月05日
    浏览(33)
  • Part1:使用 TensorFlow 和 Keras 的 NeRF计算机图形学和深度学习——计算机图形学世界中相机的工作原理

    是否有一种方法可以仅从一个场景多张不同视角的照片中捕获整个3D场景? 有。 NeRF:将场景表示为用于视图合成的神经辐射场中(NeRF: Representing Scenes as Neural Radiance Fields for View Synthesis),Mildenhall等人(2020)的论文解答了这个问题。NeRF的更简单实现赢得了 TensorFlow社区聚光

    2024年02月07日
    浏览(34)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包