003-值类型
背景
通过学习Solidity,然后输出文章检验自己的学习成果github仓库
基础知识
- 我将介绍四种在
Solidity中可用的值类型- 布尔类型(bool)
- 整数类型(uint、int)
- 地址类型(address)
- 定长字节数组类型(bytes)
- 枚举类型(enum)
布尔类型(bool)
- 布尔型的取值只有两种:
true和false - 布尔型的运算符包括:
- 比较运算符:>,>=,<,<=,==,!=
- 与运算 &&
- 或运算 ||
- 非运算 !
- && 和 ||运算符遵循短路规则,a||b,如果a是true,b不会被计算;a&&b,如果a是false,b不会被计算
- 短路规则,会更加节省gas费用
整数类型(uint、int)
uint
uint代表无符号整数,也就是说没有负数的整数- 有不同的字节数的无符号整数,可供使用
uint8范围 从 0 到uint16范围 从 0 到- ... 以
8位为递增 uint256范围 从 0 到
int
int表示有符号整数,在int中允许有负数存在int表示的范围与uint表示的范围不同int8范围 从 到int16范围 从 到- ... 以
8位为递增 int256范围 从 到
整数类型(uint、int)的运算符
- 比较运算符: <=, <, ==, !=, >=, >
- 算数运算符: +,-,-(一元运算符),*,/,%(取余),**(幂)
地址类型(address)
- address类型是一个
20字节的值 - 地址类型有两种
- 普通地址(address):可以调用
call,delegatecall和staticcall成员方法 - payable address: 比普通地址多了
transfer和send两个成员方法用于转账,和一个成员变量balance用于查询余额
- 普通地址(address):可以调用
定长字节数组类型(bytes)
bytes表示一个字节序列Solidity提供了两种字节类型:- 固定大小的字节数组
- 固定大小的字节数组属于值类型
- 固定大小的字节数组存储数据会更节省gas费用
- 动态大小的字节数组
- 动态大小的字节数组不属于值类型,在后面会讲
- 固定大小的字节数组
bytes1, bytes2, bytes3, ..., bytes32代表从1到32的字节序列bytes类型的运算符:- 比较运算符:<=, <, ==, !=, >=, >
- 位运算符: &, |, ^ (按位异或), ~ (按位取反)
- 移位运算符: << (左移位), >> (右移位)
- 索引访问: 如果
x是bytesI类型,那么当0 <= k < I时,x[k]返回第k个字节(只读)
- 移位运算符以无符号的整数类型作为右操作数(但返回左操作数的类型),它表示要移位的位数。有符号类型的移位将产生一个编译错误
- 成员变量:
.length: 这个字节数组的长度(只读)
枚举类型(enum)
- 枚举类型用于表示一组有限的值,它们对于建模选择和跟踪状态很有用
- 枚举类型的声明:
enum枚举名称 { 枚举值1, 枚举值2, ... }- 枚举值的类型是
uint8,从0开始递增,不能超过256个
- 枚举可以声明在合约外面并从其他合约中导入
- 枚举可以显式的和
uint8进行相互转换,并且会检查所转换的无符号整数是否在枚举长度范围内
默认值
- 未赋值的变量有一个默认值
布尔类型(bool)为false整数类型(uint、int)为0地址类型(address)为0x0000000000000000000000000000000000000000定长字节数组类型(bytes)为0,根据长度决定,比如bytes2为0x0000枚举类型(enum)为0
例子
该例子是值类型使用的例子
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;
contract ValueType {
bool public b = false;
bool public b1 = 1118 > 1114; // true
bool public b2 = 1118 >= 1114; // true
bool public b3 = 1118 < 1114; // false
bool public b4 = 1118 <= 1114; // false
bool public b5 = 1118 == 1114; // false
bool public b6 = 1118 != 1114; // true
bool public b7 = !b; // true
bool public b8 = b1 && b2; // true
bool public b9 = b3 && b1; // false,发生短路运算
bool public b10 = b3 || b4; // false
bool public b11 = b1 || b3; // true,发生短路运算
uint8 public u8 = 18;
uint24 public u24 = 1118;
uint public u256 = 1114; // uint是uint256的别称
int8 public i8 = - 18;
int24 public i24 = 1118;
int public i256 = - 1114; // int是int256的别称
int public minInt = type(int).min;
int public maxInt = type(int).max;
int public int_1 = - 1114;
int public int_2 = 1118 + 1114;
int public int_3 = 1118 - 1114;
int public int_4 = 18 * 14;
int public int_5 = 18 / 18;
int public int_6 = 1118 % 1114;
int public int_7 = 2 ** 10;
address public addr;
constructor ()payable{
}
function getEth() public {
addr = msg.sender;
address payable _addr = payable(addr);
_addr.transfer(1 ether);
}
bytes1 public a1 = 0xb5; // [10110101]
bytes2 public a2 = 0xb556; // [1011010101010110]
bytes1 public a3 = a1[0]; // [10110101]
enum Status{
Pending,
Shipped,
Accepted,
Rejected,
Canceled
}
Status public status;
Status public maxEnum = type(Status).max;
Status public minEnum = type(Status).min;
function get() public view returns (Status){
return status;
}
function set(Status _status) public {
status = _status;
}
function cancel() public {
status = Status.Canceled;
}
function reject() public {
status = Status.Rejected;
}
function accept() public {
status = Status.Accepted;
}
function ship() public {
status = Status.Shipped;
}
function pending() public {
status = Status.Pending;
}
function reset() public {
delete status;
delete a1;
delete b1;
delete u8;
delete i8;
delete addr;
}
bool public defaultBoo; // false
uint public defaultUint; // 0
int public defaultInt; // 0
address public defaultAddr; // 0x0000000000000000000000000000000000000000
bytes2 public defaultBytes; // 0x0000
Status public defaultEnum; // 0
}
程序解析
布尔类型(bool)使用的例子
bool public b = false;
bool public b1 = 1118 > 1114; // true
bool public b2 = 1118 >= 1114; // true
bool public b3 = 1118 < 1114; // false
bool public b4 = 1118 <= 1114; // false
bool public b5 = 1118 == 1114; // false
bool public b6 = 1118 != 1114; // true
bool public b7 = !b; // true
bool public b8 = b1 && b2; // true
bool public b9 = b3 && b1; // false,发生短路运算
bool public b10 = b3 || b4; // false
bool public b11 = b1 || b3; // true,发生短路运算
- 布尔类型(bool)运算符的使用和赋值
整数类型(uint、int)使用的例子
uint8 public u8 = 18;
uint24 public u24 = 1118;
uint public u256 = 1114; // uint是uint256的别称
int8 public i8 = - 18;
int24 public i24 = 1118;
int public i256 = - 1114; // int是int256的别称
- 整数类型(uint、int)的赋值
int public minInt = type(int).min;
int public maxInt = type(int).max;
- int的最大值和最小值
int public int_1 = - 1114;
int public int_2 = 1118 + 1114;
int public int_3 = 1118 - 1114;
int public int_4 = 18 * 14;
int public int_5 = 18 / 18;
int public int_6 = 1118 % 1114;
int public int_7 = 2 ** 10;
- 运算符的例子,如果想看运算符的例子,可以看上面
布尔类型的例子
地址类型(address)使用的例子
address public addr;
- 声明了一个地址类型(address)叫
addr
constructor ()payable{
}
constructor表示构造函数,只会在合约部署的时候,调用一次- 构造函数用
payable修饰,保证部署合约的时候,能打入eth
function getEth() public {
addr = msg.sender;
address payable _addr = payable(addr);
_addr.transfer(1 ether);
}
- 用户调用此函数,可以从合约中提取一个
ether到自己的账户,所以部署合约的时候,一定打入一个ether以上,否则调用这个函数会失败
定长字节数组类型(bytes)使用的例子
bytes1 public a1 = 0xb5; // [10110101]
bytes2 public a2 = 0xb556; // [1011010101010110]
bytes1 public a3 = a1[0]; // [10110101]
- 定长字节数组类型(bytes)的赋值
枚举类型(enum)使用的例子
enum Status{
Pending,
Shipped,
Accepted,
Rejected,
Canceled
}
Status public status;
Status public maxEnum = type(Status).max;
Status public minEnum = type(Status).min;
- Status表示发货状态,并声明了status,默认值为"Pending"
- 通过
type(Status).max和type(Status).min,可以得到枚举类型(enum)的最大值和最小值
function get() public view returns (Status) {
return status;
}
- 返回值为Status类型
- Pending为0
- Shipped为1
- Accepted为2
- Rejected为3
- Canceled为4
function set(Status _status) public {
status = _status;
}
- 通过输入uint类型数字更新status变量,若大于枚举(enum)范围,会交易失败
function cancel() public {
status = Status.Canceled;
}
- 更新status为
Canceled
function reject() public {
status = Status.Rejected;
}
- 更新status为
Rejected
function accept() public {
status = Status.Accepted;
}
- 更新status为
Accepted
function ship() public {
status = Status.Shipped;
}
- 更新status为
Shipped
function pending() public {
status = Status.Pending;
}
- 更新status为
Pending
默认值使用的例子
function reset() public {
delete status;
delete a1;
delete b1;
delete u8;
delete i8;
delete addr;
}
- 使用
delete关键字,可以将该变量,恢复成默认值
bool public defaultBoo; // false
uint public defaultUint; // 0
int public defaultInt; // 0
address public defaultAddr; // 0x0000000000000000000000000000000000000000
bytes2 public defaultBytes; // 0x0000
Status public defaultEnum; // 0
- 声明变量未赋值,变量的值是默认值