第四章 以太坊智能合约solidity介绍

这篇具有很好参考价值的文章主要介绍了第四章 以太坊智能合约solidity介绍。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

Solidity是一门面向合约的、为实现智能合约而创建的高级编程语言,设计的目的是能在以太坊虚拟机上运行。

本章大概介绍合约的基本信息,合约的组成,语法方面不做过多的介绍,个人建议多阅读官方文档效果更佳,后续的章节会开发ERC20代币合约案例以便于更好的学习智能合约的开发

官网文档:https://docs.soliditylang.org/en/v0.8.12/

中文文档:https://learnblockchain.cn/docs/solidity

1、第一个合约介绍

我们来看一个最简单的存取整形数据的合约代码

// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.4.16 <0.9.0;

contract SimpleStorage {
    uint storedData;

    function set(uint x) public {
        storedData = x;
    }

    function get() public view returns (uint) {
        return storedData;
    }
}

第一行说明源代码在GPL 3.0版权许可,在代码中加入机器可读许可证说明很重要, 在发布源代码时在默认需要,直接照抄就行。

第二行是告诉编译器源代码适用的solidity版本为>=0.4.16 <0.9.0,如果是这样定义:pragma solidity ^0.5.2,则源文件将既不允许低于 0.5.2 版本的编译器编译, 也不允许高于(包含) 0.6.0 版本的编译器编译

contract声明一个合约,类似于java的class

uint storedData声明一个类型为 uint (256位无符号整数)的状态变量,叫做storedData,这边的变量可以认为是数据库表里面的一个字段,可以通过函数进行查询和变更。

函数set和get可以用来变更或取出变量的值,function用于定义一个函数。

2、合约组成

我们推荐使用在线remix来演示solidity的语法

https://remix.ethereum.org/

合约中可以包含注释、状态变量、函数、事件Event、结构体、和枚举类型的声明,且合约可以从其他合约继承。

注释
// 这是一个单行注释。

/*
这是一个
多行注释。
*/
状态变量

状态变量是永久地存储在合约存储中的值。

// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.4.0 <0.9.0;

contract SimpleStorage {
    uint storedData; // 定义一个无符号整形的状态变量storedData
    // ...
}
函数(function)

函数是代码的可执行单元。函数通常在合约内部定义,但也可以在合约外定义。

// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.7.1 <0.9.0;

contract SimpleAuction {
	// 在合约内部定义函数
    function bid() public payable { // Function
    }
}

// 在合约外部定义函数
function helper(uint x) pure returns (uint) {
    return x * 2;
}
函数修改器modifier

函数 修改器modifier可以用来以声明的方式修改函数语义,我们看下修改器的用法

// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.4.22 <0.9.0;
contract MyPurchase {
    address public seller;
    uint256 storedData;

    modifier onlySeller() { // 定义修改器
    	// 只有当合约的调用者==seller时才执行_;的语句,_;相当于占位符
        require(msg.sender == seller,"Only seller can call this.");
        _;
    }
    
    function abort() view public onlySeller {
    	require(msg.sender == seller,"Only seller can call this.");
    	storedData == 1;
    }
}

上面的效果等同于

// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.4.22 <0.9.0;
contract MyPurchase {
    address public seller;
    uint256 storedData;
    
    function abort() view public {
    	require(msg.sender == seller,"Only seller can call this.");
    	storedData == 1;
    }
}
事件

事件是能方便地调用以太坊虚拟机日志功能的接口,客户端调用的时候可以接收该事件。

// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.4.21 <0.9.0;

contract SimpleAuction {
    
    event HighestBidIncreased(address bidder, uint amount); // Event,定义一个事件

    function bid() public payable {
        // ...
        emit HighestBidIncreased(msg.sender, msg.value); // 触发事件
    }
}
结构体

结构体可以将几个变量封装起来

// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.4.0 <0.9.0;

contract Ballot {
    struct Voter { // 结构体
        uint weight;
        bool voted;
        address delegate;
        uint vote;
    }
}
枚举类型

枚举可用来创建由一定数量的“常量值”构成的自定义类型

// SPDX-License-Identifier: GPL-3.0
pragma solidity >=0.4.0 <0.9.0;

contract Purchase {
    enum State { Created, Locked, Inactive } // Enum
}
数据类型

Solidity 是一种静态类型语言,意味着每个变量(状态变量和局部变量)都需要在编译时指定变量的类型。

Solidity 提供了几种基本类型,并且基本类型可以用来组合出复杂类型。

值类型

值类型常用的包含:布尔类型,整形,浮点型,地址类型,枚举类型等

布尔类型:使用bool定义一个波尔类型的变量

bool isOwner;

整型

int/uint:分别表示有符号和无符号的不同位数的整型变量,支持关键字 uint8uint256 (无符号,从 8 位到 256 位)以及 int8int256

uint256 storedData;

地址类型

address:保存一个20字节的值

address payable:可支付地址,payable表示可以接受以太币,如果函数内部需要用到转账功能则需要加上payable

引用类型

数组

uint[] x;

bytes和string也是数组,bytes类似与byte[]

映射

映射类型在声明时的形式为mapping(keyType => valueType),其中 _KeyType 可以是任何基本类型,即可以是任何的内建类型, bytesstring 或合约类型、枚举类型。 而其他用户定义的类型或复杂的类型如:映射、结构体、即除 bytesstring 之外的数组类型是不可以作为 _KeyType 的类型的。

mapping (address => uint256) private _balances;

3、以太币单位

以太币(Ether) 单位之间的换算就是在数字后边加上 weigweiether 来实现的,如果后面没有单位,缺省为 wei

最⼩单位: Wei (伟)

10^9 Wei = 1 Gwei

10^18 Wei = 1 Ether

4、时间单位

秒是缺省时间单位,在时间单位之间,数字后面带有 secondsminuteshoursdaysweeks 的可以进行换算,基本换算关系如下

1 == 1 seconds
1 minutes == 60 seconds
1 hours == 60 minutes
1 days == 24 hours
1 weeks == 7 days

5、特殊变量和函数

区块和交易属性
blockhash(uint blockNumber) returns (bytes32):指定区块的区块哈希——仅可用于最新的 256 个区块且不包括当前区块
block.chainid (uint): 当前链 id
block.coinbase ( address ): 挖出当前区块的矿工地址
block.difficulty ( uint ): 当前区块难度
block.gaslimit ( uint ): 当前区块 gas 限额
block.number ( uint ): 当前区块号
block.timestamp ( uint): 自 unix epoch 起始当前区块以秒计的时间戳
gasleft() returns (uint256) :剩余的 gas
msg.data ( bytes ): 完整的 calldata
msg.sender ( address ): 消息发送者(当前调用)
msg.sig ( bytes4 ): calldata 的前 4 字节(也就是函数标识符)
msg.value ( uint ): 随消息发送的 wei 的数量
tx.gasprice (uint): 交易的 gas 价格
tx.origin (address payable): 交易发起者(完全的调用链)
ABI 编码及解码函数
abi.decode(bytes memory encodedData, (...)) returns (...): 对给定的数据进行ABI解码,而数据的类型在括号中第二个参数给出 。 例如: (uint a, uint[2] memory b, bytes memory c) = abi.decode(data, (uint, uint[2], bytes))

abi.encode(...) returns (bytes): ABI - 对给定参数进行编码

abi.encodePacked(...) returns (bytes):对给定参数执行 紧打包编码 ,注意,可以不明确打包编码。

abi.encodeWithSelector(bytes4 selector, ...) returns (bytes): ABI - 对给定第二个开始的参数进行编码,并以给定的函数选择器作为起始的 4 字节数据一起返回

abi.encodeWithSignature(string signature, ...) returns (bytes):等价于abi.encodeWithSelector(bytes4(keccak256(signature), ...)

错误处理
  • assert(bool condition)

    如果不满足条件,则会导致Panic 错误,则撤销状态更改 - 用于检查内部错误。

  • require(bool condition)

    如果条件不满足则撤销状态更改 - 用于检查由输入或者外部组件引起的错误。

  • require(bool condition, string memory message)

    如果条件不满足则撤销状态更改 - 用于检查由输入或者外部组件引起的错误,可以同时提供一个错误消息。

  • revert()

    终止运行并撤销状态更改。

  • revert(string memory reason)

    终止运行并撤销状态更改,可以同时提供一个解释性的字符串。

地址成员
  • <address>.balance (uint256)

    以 Wei 为单位的 地址类型 Address 的余额。

  • <address>.code (bytes memory)

    在 地址类型 Address 上的代码(可以为空)

  • <address>.codehash (bytes32)

    :ref:[](https://learnblockchain.cn/docs/solidity/units-and-global-variables.html#id9)address的codehash

  • <address payable>.transfer(uint256 amount)

    向 地址类型 Address 发送数量为 amount 的 Wei,失败时抛出异常,使用固定(不可调节)的 2300 gas 的矿工费。

  • <address payable>.send(uint256 amount) returns (bool)

    向 地址类型 Address 发送数量为 amount 的 Wei,失败时返回 false,发送 2300 gas 的矿工费用,不可调节。

  • <address>.call(bytes memory) returns (bool, bytes memory)

    用给定的有效载荷(payload)发出低级 CALL 调用,返回成功状态及返回数据,发送所有可用 gas,也可以调节 gas。

  • <address>.delegatecall(bytes memory) returns (bool, bytes memory)

    用给定的有效载荷 发出低级 DELEGATECALL 调用 ,返回成功状态并返回数据,发送所有可用 gas,也可以调节 gas。 发出低级函数 DELEGATECALL,失败时返回 false,发送所有可用 gas,可调节。

  • <address>.staticcall(bytes memory) returns (bool, bytes memory)

    用给定的有效载荷 发出低级 STATICCALL 调用 ,返回成功状态并返回数据,发送所有可用 gas,也可以调节 gas。文章来源地址https://www.toymoban.com/news/detail-461156.html

到了这里,关于第四章 以太坊智能合约solidity介绍的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

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

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

相关文章

  • 以太坊智能合约语言Solidity - 3 数组

    1字节(Byte) = 8位 (bit), bytes32 = 256位,bytes1 实质上就等于 int8 固定长度的数组一旦被定义就无法再更改,并且长度在一开始就会被显式定义 我们再来创建一个新的文件用来编写代码 字节数组无法进行基本运算,但是可以比较 字节数组还支持其他一些逻辑运算,具体计算结果

    2023年04月08日
    浏览(62)
  • 第四章 介绍Productions - 连接选项 - 使用文件适配器的业务主机类

    针对特定场景 IRIS 提供专门的业务服务类和已经使用特定适配器的业务操作类: File adapters FTP adapters HTTP and SOAP adapters TCP adapters 要使用这些业务主机,通常不需要执行任何编码。 或实际原因,以下部分可能不会涵盖 IRIS 提供的所有专业业务主机类。要查找指定适配器的所有

    2024年02月05日
    浏览(38)
  • 以太坊智能合约开发:Solidity 语言快速入门

    在本文中,我们从一个简单的智能合约样例出发,通过对智能合约源文件结构的剖析与介绍,使大家对Solidity语言有一个初步的认识。最后,我们将该智能合约样例在 Remix 合约编译器中编译、部署,观察其执行结果。 在开始之前,我们先对Solidity有个初步的了解,即Solidity是

    2023年04月09日
    浏览(51)
  • 以太坊智能合约开发:Solidity语言中的映射

    本文我们介绍Solidity语言中的映射,包括映射的基本定义、语法、映射的变量声明和基本读写操作。并且通过两个智能合约例子演示了映射的定义与基本操作。 Solidity中关于映射的一些定义: 映射以键-值对(key = value)的形式存储数据; 键可以是任何内置数据类型,包括字节

    2024年02月05日
    浏览(56)
  • 基于以太坊的智能合约开发Solidity(基础篇)

    参考教程:基于以太坊的智能合约开发教程【Solidity】_哔哩哔哩_bilibili (1)程序编译完成后,需要在虚拟机上运行,将合约部署好后便可执行刚刚编写的函数。(注意, 合约一旦部署,就会永久存在于区块链上,且不可篡改 ,不过可以销毁) (2)执行完成后,可以得到以

    2024年02月04日
    浏览(57)
  • 以太坊智能合约开发:Solidity 语言中的数据类型

    本文我们介绍Solidity语言的数据类型,重点是值类型,包括布尔类型、整型、地址类型、字节类型、字符串类型和枚举类型。并且通过两个智能合约例子,用于演示这些数据类型的声明与使用方法。 访问 Github 仓库 获取更多资料。 Solidity中关于数据类型的定义如下: Solidity是

    2024年02月02日
    浏览(69)
  • 基于以太坊的智能合约开发Solidity(事件&日志篇)

    (1)事件用于记录在区块链上的特定活动,“emit ValueChanged(newValue);”语句的作用是触发ValueChanged事件(首先需要声明事件)。 ①触发事件后会生成相应日志,上图黄框就是“emit ValueChanged(newValue);”语句产生的日志,其中“form”指的是触发事件的合约账户。 ②事件主要是供

    2024年02月04日
    浏览(44)
  • 以太坊智能合约开发:Solidity语言中的构造函数

    Solidity语言中关于构造函数的定义: 构造函数是使用 constructor 声明的一个可选函数; 构造函数只在合约部署时调用一次,并用于初始化合约的状态变量; 如果没有显式定义的构造函数,则由编译器创建默认构造函数。 构造函数声明语法如下: 其中: ** constructor :

    2024年02月01日
    浏览(52)
  • 基于以太坊的智能合约开发Solidity(内存&结构体篇)

    参考教程:【内存、引用与持久化存储】1、内存与区块链——storage与memory原理_哔哩哔哩_bilibili (1)所有的复杂类型,即数组、结构和映射类型,都有一个额外属性——“数据位置”,用来说明数据是保存在内存memory中还是存储storage中,保存在memory中的数据,在函数执行完

    2024年02月04日
    浏览(57)
  • 玩以太坊链上项目的必备技能(初识智能合约语言-Solidity之旅一)

    前面一篇关于 智能合约 翻译文讲到了,是一种计算机程序,既然是程序,那就可以使用 程序语言 去编写 智能合约 了。 而若想玩区块链上的项目,大部分区块链项目都是开源的,能看得懂 智能合约 代码,或找出其中的漏洞,那么,学习 Solidity 这门高级的智能合约语言是有

    2023年04月16日
    浏览(96)

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

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

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

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

二维码1

领取红包

二维码2

领红包