如需获取本内容的最新版本,请参见 Cyfrin.io 上的Error(代码示例)
错误将撤销交易期间对状态所做的所有更改。
您可以通过调用require、revert或assert来抛出错误。
require用于在执行前验证输入和条件。revert与require类似。详情请参阅下面的代码。assert用于检查永远不应为假的代码。断言失败可能意味着存在错误。
使用自定义错误以节省gas费用。
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.26;
contract Error {
function testRequire(uint256 _i) public pure {
// Require 应用于验证以下条件:
// - 输入
// - 执行前的条件
// - 其他函数调用的返回值
require(_i > 10, "Input must be greater than 10");
}
function testRevert(uint256 _i) public pure {
// 当需要检查的条件很复杂时,Revert 非常有用。
// 这段代码的功能与上面的示例完全相同
if (_i <= 10) {
revert("Input must be greater than 10");
}
}
uint256 public num;
function testAssert() public view {
/ /断言应仅用于检测内部错误和验证不变量。
// 我们断言num始终等于0, 因为无法更新num的值
assert(num == 0);
}
// 自定义 error
error InsufficientBalance(uint256 balance, uint256 withdrawAmount);
function testCustomError(uint256 _withdrawAmount) public view {
uint256 bal = address(this).balance;
if (bal < _withdrawAmount) {
revert InsufficientBalance({
balance: bal,
withdrawAmount: _withdrawAmount
});
}
}
}
Remix Lite 尝试一下
这是另一个例子
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.26;
contract Account {
uint256 public balance;
uint256 public constant MAX_UINT = 2 ** 256 - 1;
function deposit(uint256 _amount) public {
uint256 oldBalance = balance;
uint256 newBalance = balance + _amount;
// balance + _amount 不会溢出,如果balance + _amount >= oldBalance
require(newBalance >= oldBalance, "Overflow");
balance = newBalance;
assert(balance >= oldBalance);
}
function withdraw(uint256 _amount) public {
uint256 oldBalance = balance;
// balance - _amount 不会下溢,如果balance >= _amount
require(balance >= _amount, "Underflow");
if (balance < _amount) {
revert("Underflow");
}
balance -= _amount;
assert(balance <= oldBalance);
}
}
Remix Lite 尝试一下
END