Solidity,Member "transfer" 未找到或在依赖参数后不可见
Solidity, Member "transfer" not found or not visible after argument-dependent
使用 Solidity ^0.5.0,
我实际上正在尝试实现在 ^0.4.17 中工作的旧代码,但它在 Remix 上抛出错误。
我检查了语法和所有内容,但就是无法发现问题所在。
非常感谢任何帮助。
pragma solidity ^0.5.0;
contract Lottery{
address public manager;
address[] public players;
constructor() public {
manager = msg.sender;
}
function participate() public payable {
require(msg.value > .01 ether);
players.push(msg.sender);
}
function pseudoRandom() private view returns(uint){
return uint(keccak256(abi.encodePacked(block.difficulty, now, players)));
}
function pickWinner() public {
uint index = pseudoRandom() % players.length;
players[index].transfer(address(this).balance);
}
}
这是错误消息:
browser/Lottery.sol:22:8: TypeError: Member "transfer" not found or not visible after argument-dependent
在地址中查找。
玩家[索引].transfer(地址(msg.sender).balance);
^--------------------^
请参阅Solidity v0.5.0 Breaking Changes。
正如所指出的here:
The address type was split into address and address payable, where only address payable provides the transfer function.
查看我的回答here了解更多详情。
更改此行:
address[] public players;
为此:
address payable[] public players;
编辑
谢谢smarx!
您在初始声明中缺少应付修饰符。
更改
address[] public players;
到
address payable[] public players;
据我了解,从你的合约业务逻辑来看,所有参与抽奖的地址都不会中奖,所以你不需要将所有地址都设置为可支付。
更好的方法是通过将地址类型转换为可支付地址来仅使获胜者地址可支付,如下所示。
address payable winnerAddress = payable(players[index]);
winnerAddress.transfer(address(this).balance);
这是整个合约代码的样子
// SPDX-License-Identifier: GPL-3.0
pragma solidity ^0.8.9;
contract Lottery {
address public manager;
address payable[] public players;
constructor() { }
function lottery() public {
manager = msg.sender;
}
function enter() public payable {
require(msg.value > .01 ether);
players.push(payable(msg.sender));
}
function random() public view returns (uint8) {
return uint8(uint256(keccak256(abi.encodePacked(block.timestamp, block.difficulty, players)))%251);
}
function pickWinner() public {
uint index = random() % players.length;
players[index].transfer(address(this).balance);
}
}
使用 Solidity ^0.5.0, 我实际上正在尝试实现在 ^0.4.17 中工作的旧代码,但它在 Remix 上抛出错误。 我检查了语法和所有内容,但就是无法发现问题所在。 非常感谢任何帮助。
pragma solidity ^0.5.0;
contract Lottery{
address public manager;
address[] public players;
constructor() public {
manager = msg.sender;
}
function participate() public payable {
require(msg.value > .01 ether);
players.push(msg.sender);
}
function pseudoRandom() private view returns(uint){
return uint(keccak256(abi.encodePacked(block.difficulty, now, players)));
}
function pickWinner() public {
uint index = pseudoRandom() % players.length;
players[index].transfer(address(this).balance);
}
}
这是错误消息:
browser/Lottery.sol:22:8: TypeError: Member "transfer" not found or not visible after argument-dependent 在地址中查找。
玩家[索引].transfer(地址(msg.sender).balance);
^--------------------^
请参阅Solidity v0.5.0 Breaking Changes。
正如所指出的here:
The address type was split into address and address payable, where only address payable provides the transfer function.
查看我的回答here了解更多详情。
更改此行:
address[] public players;
为此:
address payable[] public players;
编辑
谢谢smarx!
您在初始声明中缺少应付修饰符。 更改
address[] public players;
到
address payable[] public players;
据我了解,从你的合约业务逻辑来看,所有参与抽奖的地址都不会中奖,所以你不需要将所有地址都设置为可支付。 更好的方法是通过将地址类型转换为可支付地址来仅使获胜者地址可支付,如下所示。
address payable winnerAddress = payable(players[index]);
winnerAddress.transfer(address(this).balance);
这是整个合约代码的样子
// SPDX-License-Identifier: GPL-3.0
pragma solidity ^0.8.9;
contract Lottery {
address public manager;
address payable[] public players;
constructor() { }
function lottery() public {
manager = msg.sender;
}
function enter() public payable {
require(msg.value > .01 ether);
players.push(payable(msg.sender));
}
function random() public view returns (uint8) {
return uint8(uint256(keccak256(abi.encodePacked(block.timestamp, block.difficulty, players)))%251);
}
function pickWinner() public {
uint index = random() % players.length;
players[index].transfer(address(this).balance);
}
}