Error
Solidity 文件中的範例原始碼錯誤
新手來了 我正在嘗試將此處顯示在乙太坊網站上的範例購買契約部署到http://remix.ethereum.org/的線上 Remix Solidity 編譯器。
但是當我複制/粘貼編寫的範常式式碼時,我收到以下錯誤消息。
錯誤資訊
browser/purchase.sol:62:25:警告:不推薦使用從地址類型繼承的合約成員“餘額”。將合約轉換為“address”類型以訪問成員,例如使用“address(contract).balance”代替。
seller.transfer(this.balance); ^----------^
任何人都可以幫助糾正我下面的程式碼嗎?我已經展示了我的工作和我已經嘗試過的兩件事,但都沒有成功。
購買.sol
pragma solidity ^0.4.22; contract Purchase { uint public value; address public seller; address public buyer; enum State { Created, Locked, Inactive } State public state; // Ensure that `msg.value` is an even number. // Division will truncate if it is an odd number. // Check via multiplication that it wasn't an odd number. constructor() public payable { seller = msg.sender; value = msg.value / 2; require((2 * value) == msg.value, "Value has to be even."); } modifier condition(bool _condition) { require(_condition); _; } modifier onlyBuyer() { require( msg.sender == buyer, "Only buyer can call this." ); _; } modifier onlySeller() { require( msg.sender == seller, "Only seller can call this." ); _; } modifier inState(State _state) { require( state == _state, "Invalid state." ); _; } event Aborted(); event PurchaseConfirmed(); event ItemReceived(); /// Abort the purchase and reclaim the ether. /// Can only be called by the seller before /// the contract is locked. function abort() public onlySeller inState(State.Created) { emit Aborted(); state = State.Inactive; seller.transfer(this.balance); // original attempt, yields below error // seller.transfer(address(contract).balance); // first unsuccessful attempt to correct // address(contract).balance; // second unsuccessful attempt to correct } /// Confirm the purchase as buyer. /// Transaction has to include `2 * value` ether. /// The ether will be locked until confirmReceived /// is called. function confirmPurchase() public inState(State.Created) condition(msg.value == (2 * value)) payable { emit PurchaseConfirmed(); buyer = msg.sender; state = State.Locked; } /// Confirm that you (the buyer) received the item. /// This will release the locked ether. function confirmReceived() public onlyBuyer inState(State.Locked) { emit ItemReceived(); // It is important to change the state first because // otherwise, the contracts called using `send` below // can call in again here. state = State.Inactive; // NOTE: This actually allows both the buyer and the seller to // block the refund - the withdraw pattern should be used. buyer.transfer(value); seller.transfer(this.balance); } }
評論摘要。
修正後的程式碼如下。
購買.sol
pragma solidity ^0.4.22; contract Purchase { uint public value; address public seller; address public buyer; enum State { Created, Locked, Inactive } State public state; // Ensure that `msg.value` is an even number. // Division will truncate if it is an odd number. // Check via multiplication that it wasn't an odd number. constructor() public payable { seller = msg.sender; value = msg.value / 2; require((2 * value) == msg.value, "Value has to be even."); } modifier condition(bool _condition) { require(_condition); _; } modifier onlyBuyer() { require( msg.sender == buyer, "Only buyer can call this." ); _; } modifier onlySeller() { require( msg.sender == seller, "Only seller can call this." ); _; } modifier inState(State _state) { require( state == _state, "Invalid state." ); _; } event Aborted(); event PurchaseConfirmed(); event ItemReceived(); /// Abort the purchase and reclaim the ether. /// Can only be called by the seller before /// the contract is locked. function abort() public onlySeller inState(State.Created) { emit Aborted(); state = State.Inactive; //seller.transfer(this.balance); // throws error seller.transfer(address(this).balance); // fixes error } /// Confirm the purchase as buyer. /// Transaction has to include `2 * value` ether. /// The ether will be locked until confirmReceived /// is called. function confirmPurchase() public inState(State.Created) condition(msg.value == (2 * value)) payable { emit PurchaseConfirmed(); buyer = msg.sender; state = State.Locked; } /// Confirm that you (the buyer) received the item. /// This will release the locked ether. function confirmReceived() public onlyBuyer inState(State.Locked) { emit ItemReceived(); // It is important to change the state first because // otherwise, the contracts called using `send` below // can call in again here. state = State.Inactive; // NOTE: This actually allows both the buyer and the seller to // block the refund - the withdraw pattern should be used. buyer.transfer(value); //seller.transfer(this.balance); // throws error seller.transfer(address(this).balance); // fixes error } }
屬性餘額與特定地址相關聯,而不是與合約本身相關聯。當你說 this.balance 時,它試圖呼叫合約的 balance 屬性,但它應該是 address(this).balance。這將使您能夠訪問合約地址的餘額。