在比較下面合約中的兩個方法時:
contract MyTest {
uint256 public nonce = 0;
mapping(address => mapping(uint256 => MyStruct)) public getStructByNonceByAccount;
constructor(uint256 value_, bool isTrue_) {
MyStruct memory _myStruct;
_myStruct.account = msg.sender;
_myStruct.value = value_;
_myStruct.isTrue = isTrue_;
getStructByNonceByAccount[msg.sender][nonce] = _myStruct;
nonce++;
}
function getMyStructAttributes() external view returns(address, uint256, bool) {
address account = getStructByNonceByAccount[msg.sender][0].account;
uint256 value = getStructByNonceByAccount[msg.sender][0].value;
bool isTrue = getStructByNonceByAccount[msg.sender][0].isTrue;
return (account, value, isTrue);
}
function getMyStructAttributesWithTempStorage() external view returns(address, uint256, bool) {
MyStruct storage myStruct = getStructByNonceByAccount[msg.sender][0];
address account = myStruct.account;
uint256 value = myStruct.value;
bool isTrue = myStruct.isTrue;
return (account, value, isTrue);
}
}
| 函數(shù) | 寫入類型 | gas消耗量 |
|---|---|---|
| getMyStructAttributes | 重復(fù)索引 | 7528 |
| getMyStructAttributesWithTempStorage | 以storage變量為中繼 | 7291 |
可以發(fā)現(xiàn)第二個方法 getMyStructAttributesWithTempStorage()更節(jié)約gas。原因如下:
在第一個方法 getMyStructAttributes() 中,我們在每次調(diào)用該函數(shù)時都要使用 getStructByNonceByAccount()函數(shù)查詢映射中的值,并將其存儲在新的變量中。這意味著我們需要進行多次映射查詢和多次變量分配,從而增加了燃氣成本。
而在第二個方法 getMyStructAttributesWithTempStorage()中,我們首先將 MyStruct 變量存儲在一個Storage變量中,然后使用該Storage變量進行映射訪問和屬性查詢。這減少了映射訪問和變量分配的次數(shù),從而減少了燃氣成本。
因此,第二個方法更節(jié)約gas。雖然節(jié)約的gas有限,但是第二種方法能使得代碼更為簡潔,因此很鼓勵使用。