Solidity

for循環有什麼替代方案嗎?

  • October 29, 2020

我在 NFT 合約的 burn() 函式中使用過。

function burn(address to, uint256 tokenId) external {
   require(_exists(tokenId), "Contract: operator query for nonexistent token");
   
   for (uint256 i = 0; i < _tokenIds.length; i ++) {
       if (_tokenIds[i] == tokenId) {
           _tokenIds[i] = _tokenIds[_tokenIds.length - 1];
           _tokenIds.pop();
       }
   }
   
   // Clear metadata (if any)
   delete _Info[tokenId];
   delete _tokenOwnersMap[tokenId];
   delete _tokenApprovalsMap[tokenId];

   emit Burn(to, tokenId);
}

根據網際網路上的一些資源,循環和刪除的使用會導致更多的gas消耗,對嗎?刪除的任何其他選擇?

不完全正確。事實上,delete 降低了gas成本。例如,在這裡閱讀有關 gas 退款的資訊:https ://ethereum.stackexchange.com/a/859/31933

有問題的部分是循環。這有兩個主要問題:

  1. 如果您基於數組的長度(或任何未預先確定的值)循環,如果有很多條目並且交易用完氣體,則循環可能會執行太久
  2. 由於循環,需要循環的結構通常使用起來很昂貴

根據要求,有時可以刪除循環(及其數組)並改用映射。但只有當您的資料結構可以用映射表示並且您真的不需要迭代它(您不能迭代映射)時,這才是正確的。

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