Solidity

將 uint 值設置為零的問題

  • May 8, 2018

我用solidity瀏覽器做了一些智能合約,這是我的程式碼:

pragma solidity ^0.4.0;

contract Test {
   struct User {
       string name;
       string surname;
       uint active;
   }

   mapping(bytes32 => User) public userRegister;

   function add_user(string _name, string _surname) {
       bytes32 _hc=sha3(_name, _surname);
       User p = userRegister[_hc];  

       p.name=_name;
       p.surname=_surname;
       p.active=1;
   }

   function remove(string _name, string _surname)  {
       bytes32 _hc=sha3(_name, _surname);
       userRegister[_hc].active=0;  
   }

   function active(string _name, string _surname)  {
       bytes32 _hc=sha3(_name, _surname);
       userRegister[_hc].active=1;  
   }
}

當我使用“JavaScript VM”時一切都很好,但是當我使用 Injected Web3 編譯契約時出現了問題。

添加使用者(使用 add_user)沒關係,但是當我嘗試刪除使用者時,出現錯誤:回調不包含結果錯誤:氣體不足

經過一些測試後,我認為當我嘗試將 uint 值設置為零時會給出錯誤。

然後我嘗試將 0 更改為

userRegister[_hc].active=0;

9(或其他整數)

userRegister[_hc].active=9; 

一切正常。

那麼,有人可以告訴我將 uint 值設置為 0 有什麼問題嗎?以及如何將 uint 變數重新設置為零?謝謝

概括

這似乎是 Browser Solidity 與geth. 當我部署契約並直接在 中執行交易時geth,契約按預期工作。

@PietroR91,請將您的程式碼作為問題送出到 Browser Solidity github。如果你不能這樣做,我可以稍後再做。


細節

環境

Browser Solidity 中的錯誤已通過編譯指示和編譯器進行驗證^0.4.0^0.4.4並且^0.4.7.

geth我使用的環境是 OS/X 上的 1.5.5-stable 版本。

修改後的原始碼

這是您的原始碼,通過添加來修改getUser(...)以檢查映射中數據的值,以及一些小的格式更改:

pragma solidity ^0.4.0;

contract Test {
   struct User {
       string name;
       string surname;
       uint active;
   }

   mapping (bytes32 => User) public userRegister;

   function add_user(string _name, string _surname) {
       bytes32 _hc = sha3(_name, _surname);
       User p = userRegister[_hc];
       p.name = _name;
       p.surname = _surname;
       p.active = 1;
   }

   function remove(string _name, string _surname)  {
       bytes32 _hc = sha3(_name, _surname);
       userRegister[_hc].active = 0;
   }

   function active(string _name, string _surname)  {
       bytes32 _hc=sha3(_name, _surname);
       userRegister[_hc].active = 1;
   }

   function getUser(string _name, string _surname) constant
     returns (string name, string surname, uint256 active) {
       bytes32 _hc = sha3(_name, _surname);
       name = userRegister[_hc].name;
       surname = userRegister[_hc].surname;
       active = userRegister[_hc].active;
   }
}

瀏覽器 Solidity - 部署和執行add_user(...)

在此處輸入圖像描述

瀏覽器 Solidity - 嘗試執行remove(...)

嘗試remove(...)在 Browser Solidity中執行時,callback contain no result Error: Intrinsic gas too low會顯示該消息。

在此處輸入圖像描述

瀏覽器 Solidity - Web3 部署

以下是 Browser Solidity 的 Web3 部署程式碼:

var testContract = web3.eth.contract([{"constant":true,"inputs":[{"name":"","type":"bytes32"}],"name":"userRegister","outputs":[{"name":"name","type":"string"},{"name":"surname","type":"string"},{"name":"active","type":"uint256"}],"payable":false,"type":"function"},{"constant":false,"inputs":[{"name":"_name","type":"string"},{"name":"_surname","type":"string"}],"name":"add_user","outputs":[],"payable":false,"type":"function"},{"constant":false,"inputs":[{"name":"_name","type":"string"},{"name":"_surname","type":"string"}],"name":"remove","outputs":[],"payable":false,"type":"function"},{"constant":true,"inputs":[{"name":"_name","type":"string"},{"name":"_surname","type":"string"}],"name":"getUser","outputs":[{"name":"name","type":"string"},{"name":"surname","type":"string"},{"name":"active","type":"uint256"}],"payable":false,"type":"function"},{"constant":false,"inputs":[{"name":"_name","type":"string"},{"name":"_surname","type":"string"}],"name":"active","outputs":[],"payable":false,"type":"function"}]);
var test = testContract.new(
  {
    from: web3.eth.accounts[0], 
    data: '0x606060405234610000575b610aae806100196000396000f300606060405263ffffffff60e060020a60003504166312f8ed308114610050578063400462fa1461016b57806344590a7e146101fd57806383e6858f1461028f57806398f5be8714610418575b610000565b34610000576100606004356104aa565b604080519081018290526060808252845460026000196101006001841615020190911604908201819052819060208201906080830190879080156100e55780601f106100ba576101008083540402835291602001916100e5565b820191906000526020600020905b8154815290600101906020018083116100c857829003601f168201915b50508381038252855460026000196101006001841615020190911604808252602090910190869080156101595780601f1061012e57610100808354040283529160200191610159565b820191906000526020600020905b81548152906001019060200180831161013c57829003601f168201915b50509550505050505060405180910390f35b34610000576101fb600480803590602001908201803590602001908080601f0160208091040260200160405190810160405280939291908181526020018383808284375050604080516020601f89358b018035918201839004830284018301909452808352979998810197919650918201945092508291508401838280828437509496506104c595505050505050565b005b34610000576101fb600480803590602001908201803590602001908080601f0160208091040260200160405190810160405280939291908181526020018383808284375050604080516020601f89358b018035918201839004830284018301909452808352979998810197919650918201945092508291508401838280828437509496506106d995505050505050565b005b346100005761031f600480803590602001908201803590602001908080601f0160208091040260200160405190810160405280939291908181526020018383808284375050604080516020601f89358b0180359182018390048302840183019094528083529799988101979196509182019450925082915084018382808284375094965061079895505050505050565b6040805190810182905260608082528451908201528351819060208083019160808401918801908083838215610370575b80518252602083111561037057601f199092019160209182019101610350565b505050905090810190601f16801561039c5780820380516001836020036101000a031916815260200191505b50838103825285518152855160209182019187019080838382156103db575b8051825260208311156103db57601f1990920191602091820191016103bb565b505050905090810190601f1680156104075780820380516001836020036101000a031916815260200191505b509550505050505060405180910390f35b34610000576101fb600480803590602001908201803590602001908080601f0160208091040260200160405190810160405280939291908181526020018383808284375050604080516020601f89358b018035918201839004830284018301909452808352979998810197919650918201945092508291508401838280828437509496506109bf95505050505050565b005b60006020819052908152604090206002810154600182019083565b6000600083836040518083805190602001908083835b602083106104fa5780518252601f1990920191602091820191016104db565b51815160209384036101000a600019018019909216911617905285519190930192850191508083835b602083106105425780518252601f199092019160209182019101610523565b6001836020036101000a0380198251168184511680821785525050505050509050019250505060405180910390209150600060008360001916600019168152602001908152602001600020905083816000019080519060200190828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f106105dd57805160ff191683800117855561060a565b8280016001018555821561060a579182015b8281111561060a5782518255916020019190600101906105ef565b5b5061062b9291505b808211156106275760008155600101610613565b5090565b505082816001019080519060200190828054600181600116156101000203166002900490600052602060002090601f016020900481019282601f1061067b57805160ff19168380011785556106a8565b828001600101855582156106a8579182015b828111156106a857825182559160200191906001019061068d565b5b506106c99291505b808211156106275760008155600101610613565b5090565b5050600160028201555b50505050565b600082826040518083805190602001908083835b6020831061070c5780518252601f1990920191602091820191016106ed565b51815160209384036101000a600019018019909216911617905285519190930192850191508083835b602083106107545780518252601f199092019160209182019101610735565b51815160209384036101000a60001901801990921691161790526040805192909401829003909120600081815291829052928120600201555093505050505b505050565b602060405190810160405280600081525060206040519081016040528060008152506000600085856040518083805190602001908083835b602083106107ef5780518252601f1990920191602091820191016107d0565b51815160209384036101000a600019018019909216911617905285519190930192850191508083835b602083106108375780518252601f199092019160209182019101610818565b518151600019602094850361010090810a8201928316921993909316919091179092526040805196909401869003862060008181528085528590208054601f600260018316159095029095011692909204928301849004840287018401909452818652929850939650909450919250508301828280156108f85780601f106108cd576101008083540402835291602001916108f8565b820191906000526020600020905b8154815290600101906020018083116108db57829003601f168201915b50505060008481526020818152604091829020600190810180548451600260001994831615610100029490940190911692909204601f81018490048402830184019094528382529599509493509091508301828280156109995780601f1061096e57610100808354040283529160200191610999565b820191906000526020600020905b81548152906001019060200180831161097c57829003601f168201915b50505060008481526020819052604090206002015492955091935050505b509250925092565b600082826040518083805190602001908083835b602083106109f25780518252601f1990920191602091820191016109d3565b51815160209384036101000a600019018019909216911617905285519190930192850191508083835b60208310610a3a5780518252601f199092019160209182019101610a1b565b51815160209384036101000a6000190180199092169116179052604080519290940182900390912060008181529182905292902060016002909101555093505050505b5050505600a165627a7a72305820a6692301b30e1302f9b8c77813503eb5f8e127531e5903cffcf70070af2e9a7a0029', 
    gas: '4700000'
  }, function (e, contract){
   console.log(e, contract);
   if (typeof contract.address !== 'undefined') {
        console.log('Contract mined! address: ' + contract.address + ' transactionHash: ' + contract.transactionHash);
   }
})

部署合約geth

我將上一節中的 Web3 Deploy 程式碼粘貼到我的開發geth控制台中:

I0106 08:17:04.067480 internal/ethapi/api.go:1045] Tx(0x2ce868c7e3377f4330ef847747b471c5ff27384b67e973fff2c86f3547316db6) created: 0x22718021ba1f0ce28931c3d0653f624c6b409763
null [object Object]
undefined
...
null [object Object]
Contract mined! address: 0x22718021ba1f0ce28931c3d0653f624c6b409763 transactionHash: 0x2ce868c7e3377f4330ef847747b471c5ff27384b67e973fff2c86f3547316db6

執行函式geth

然後我在中執行了以下功能geth

> test.add_user("test_name", "test_surname", {from: eth.accounts[0], gas: 400000});
I0106 08:19:07.999559 internal/ethapi/api.go:1047] Tx(0xda430dd968ce3537ed29b4e57ff6f10a4feb6fb674ac1f50ac5684368b9415c1) to: 0x22718021ba1f0ce28931c3d0653f624c6b409763
"0xda430dd968ce3537ed29b4e57ff6f10a4feb6fb674ac1f50ac5684368b9415c1"
...
> eth.getTransactionReceipt("0xda430dd968ce3537ed29b4e57ff6f10a4feb6fb674ac1f50ac5684368b9415c1")
{
 blockHash: "0x02e8f2b1385bafb4336a8057640967763e05ad430c47a169ce0512f5e3bc9859",
 blockNumber: 5878,
 contractAddress: null,
 cumulativeGasUsed: 85340,
 from: "0x000d1009bd8f0b1301cc5edc28ed1222a3ce671e",
 gasUsed: 85340,
 logs: [],
 logsBloom: "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
 root: "0x28b34cf11c24cc9dc72ea47539b556ce8266fa5d4bed8910da24783019e6f9cb",
 to: "0x22718021ba1f0ce28931c3d0653f624c6b409763",
 transactionHash: "0xda430dd968ce3537ed29b4e57ff6f10a4feb6fb674ac1f50ac5684368b9415c1",
 transactionIndex: 0
}

檢查函式是否正確執行:

> test.getUser("test_name", "test_surname");
["test_name", "test_surname", 1]

現在讓我們執行remove(...)有問題的函式:

> test.remove("test_name", "test_surname", {from: eth.accounts[0], gas: 400000});
I0106 08:22:30.226885 internal/ethapi/api.go:1047] Tx(0x684c27aac5ff70c97c374646de9ec376ad2a2b67c7e0205445ed208b1b95b30b) to: 0x22718021ba1f0ce28931c3d0653f624c6b409763
"0x684c27aac5ff70c97c374646de9ec376ad2a2b67c7e0205445ed208b1b95b30b"
...
> eth.getTransactionReceipt("0x684c27aac5ff70c97c374646de9ec376ad2a2b67c7e0205445ed208b1b95b30b")
{
 blockHash: "0x895f68c8d0aa3adf2ec86e22ddc4f7ca9b185252258374430ff96988646ae7a0",
 blockNumber: 5899,
 contractAddress: null,
 cumulativeGasUsed: 14828,
 from: "0x000d1009bd8f0b1301cc5edc28ed1222a3ce671e",
 gasUsed: 14828,
 logs: [],
 logsBloom: "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
 root: "0x4f21b21ed39fc110bc8c2e9e5ac3be3576c1733c59660f728bd180273dd16210",
 to: "0x22718021ba1f0ce28931c3d0653f624c6b409763",
 transactionHash: "0x684c27aac5ff70c97c374646de9ec376ad2a2b67c7e0205445ed208b1b95b30b",
 transactionIndex: 0
}

檢查函式是否正確執行:

> test.getUser("test_name", "test_surname");
["test_name", "test_surname", 0]

一個有趣的觀察

如果我修改remove(...)以添加以下內容:

function remove(string _name, string _surname)  {
   bytes32 _hc = sha3(_name, _surname);
   userRegister[_hc].name = _name;
   userRegister[_hc].surname = _surname;
   userRegister[_hc].active = 0;
}

我可以在 Browser Solidity 中執行該函式,但返回 fromgetUser(...)顯示 active 的值沒有從 1 修改為 0。

remove(...)在 Browser Solidity 中執行修改後的功能

以下螢幕顯示了remove(...)在 Browser Solidity 中成功執行的功能:

在此處輸入圖像描述

以下是交易收據geth

> eth.getTransactionReceipt("0x59734b415f6e1094f57b07579cfaba53325321f1cee9512c84c4b257ed222d3c")
{
 blockHash: "0x91949c01a0bf15a8d8cf558b9e9afcda686855669960c5aaf46069d9d75d5c82",
 blockNumber: 5949,
 contractAddress: null,
 cumulativeGasUsed: 85468,
 from: "0x000d1009bd8f0b1301cc5edc28ed1222a3ce671e",
 gasUsed: 85468,
 logs: [],
 logsBloom: "0x00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000",
 root: "0x2bf9db658636a8de8af1d4f171c8b8ea97d11bf55592d0fce67b69f3947719a6",
 to: "0x49472fa49f6e3e84c0c038416f000eaeddb5c891",
 transactionHash: "0x59734b415f6e1094f57b07579cfaba53325321f1cee9512c84c4b257ed222d3c",
 transactionIndex: 0
}

以下螢幕顯示了getUser(...)結果未更改的第二次呼叫。active仍然1不是預期的0

在此處輸入圖像描述

引用自:https://ethereum.stackexchange.com/questions/11149