3

EVM中循环的成本是多少

 2 years ago
source link: https://learnblockchain.cn/question/3053
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.
neoserver,ios ssh client

EVM中循环的成本是多少

写了个排序合约,采用链表的方式保存
不知道到了后期链表越来越长,会不会造成后面的用户进来,交互一次的GAS直接爆炸,因为交互的时候需要循环遍历链表,然后把数据插入到指定的位置
?

最佳答案 1天前

遍历链表的 gas随链表长度增长而增长,很容易触及 gas limit 限制。

你可以尝试把找插入位置查找放在链下, 然后在链上验证位置是否正确。

Tiny熊 - 布道者
擅长:智能合约,以太坊 | 采纳率 40% | 回答于 1天前

其它 1 个回答

1312930610 1天前

代码如下,我好像已经看到GAS爆炸的一幕了?

//按dna大小排列的链表
    mapping(uint256 => uint256) private mNextStudents;
    //链表的头
    uint256 private constant GUARD = 10000;

    constructor() public {
        mNextStudents[GUARD] = GUARD;
    }

    //prevTokenid.dna大于等于_newDna且_newDna>_nextTokenid.dna
    function _verifyIndex(
        uint256 _prevTokenid,
        uint256 _newDna,
        uint256 _nextTokenid
    ) private view returns (bool) {
        return
            (_prevTokenid == GUARD || mTigers[_prevTokenid].dna >= _newDna) &&
            (_nextTokenid == GUARD || _newDna > mTigers[_nextTokenid].dna);
    }

    //遍历寻找当前插入位置
    function _findIndex(uint256 _newDna) private view returns (uint256) {
        uint256 tokenid = GUARD;
        while (true) {
            if (_verifyIndex(tokenid, _newDna, mNextStudents[tokenid])) {
                return tokenid;
            }
            tokenid = mNextStudents[tokenid];
        }
    }

    //添加NFT链表
    function _addTiger(uint256 _tokenid) private {
        uint256 tokenid = _findIndex(mTigers[_tokenid].dna);
        //指向tokenid原先指向的id
        mNextStudents[_tokenid] = mNextStudents[tokenid];
        //tokenid指向当前ID
        mNextStudents[tokenid] = _tokenid;
    }

    //获取排名
    function _getTop(uint256 _top)
        internal
        view
        virtual
        returns (uint256[] memory _res)
    {
        _res = new uint256[](_top);
        uint256 tokenid = mNextStudents[GUARD];
        for (uint256 i = 0; i < _top; i++) {
            if (tokenid != GUARD) {
                _res[i] = tokenid;
                tokenid = mNextStudents[tokenid];
            } else {
                _res[i] = 999;
            }
        }
    }
您需要登录后才可以回答问题,登录 或者 注册

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK