有时候你可能希望在一个以太坊交易中向数百甚至上千个地址转以太币或者ERC20代币,但是以太坊的原生接口只支持一对一的转账,如果你采用循环的方式逐个执行转账交易,将耗费大量资金来支付gas,而且有可能超过单个区块的gas上限。本文将介绍如何只支付一次交易费就可以向多个地址发送以太币或ERC20代币。
基本的思路是使用一个智能合约,把目标地址作为参数传入智能合约的方法,让合约来帮我们执行交易:由于我们只需要调用一次合约的方法,因此只需要支付一次交易gas费用,智能合约的内部交易则不需要支付手续费。
整个交易流程看起来是这样:
|
|---transfer---> address 1#
|---transfer---> address 2#
DApp --multiTransfer--> Contract --|....
|....
|---transfer---> address N#
|
下面是以太币一对多交易的合约实现代码:
pragma solidity ^0.4.18;
contract WizSendContract{
//一对多以太币转账事件
event MultiTransfer(
address indexed _from,
uint indexed _value,
address _to,
uint _amount
);
//一对多以太币转账方法
function multiTransfer(
address[] _addresses,
uint[] _amounts
) payable public{
uint toReturn = msg.value;
for (uint i = 0; i < _addresses.length; i++) {
_addresses[i].transfer(_amounts[i]);
toReturn = toReturn - _amounts[i];
MultiTransfer(msg.sender, msg.value, _addresses[i], _amounts[i]);
}
_safeTransfer(msg.sender, toReturn);
}
}
注意:这是一个教学目的的概念验证/PoC代码,请勿直接应用于生产环境。
下面是以太坊ERC20代币一对多交易的合约实现代码:
pragma solidity ^0.4.18;
//引入ERC20定义
import "erc20.sol";
contract WizSendContract{
//一对多代币转账事件
event MultiERC20Transfer(
address indexed _from,
uint indexed _value,
address _to,
uint _amount,
ERC20 _token
);
//一对多代币转账方法
function multiERC20Transfer(
ERC20 _token,
address[] _addresses,
uint[] _amounts
) public {
for (uint i = 0; i < _addresses.length; i++) {
_token.transferFrom(msg.sender, _addresses[i], _amounts[i]);
MultiERC20Transfer(
msg.sender,
msg.value,
_addresses[i],
_amounts[i],
_token
);
}
}
}
注意:这是一个教学目的的概念验证/PoC代码,请勿直接应用于生产环境。
如果想学习区块链并在Blockchain Technologies建立职业生涯,可以看一下汇智网提供的以太坊、比特币、EOS、Fabric等区块链相关的交互式在线编程实战教程: