Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Does anArray.length-- delete the last element? #4802

Closed
fulldecent opened this issue Aug 12, 2018 · 3 comments
Closed

Does anArray.length-- delete the last element? #4802

fulldecent opened this issue Aug 12, 2018 · 3 comments

Comments

@fulldecent
Copy link
Contributor

Normally I send questions to StackOverflow.

But here I see an assertion that calling .length-- on an array will delete the last element and recover gas.

https://github.com/OpenZeppelin/openzeppelin-solidity/blob/master/contracts/token/ERC721/ERC721Token.sol#L151

The people on that team are generally smart so I'm going to assume it is true.

If it is true then can the documentation please be update to explain this feature?

@chriseth
Copy link
Contributor

Yes, it will delete the last element and then reduce the size by one. What happens is explained in the code snippet in https://solidity.readthedocs.io/en/v0.4.24/types.html#members but we should probably clarify what "resize" means in the description of the length member.

@fulldecent
Copy link
Contributor Author

Ok, I learned two interesting things today.

  • The complexity of array.length = x is O(1) if x > array.length and it is O(n) if x < array.length.
  • Calling .length-- on an empty array will set the length to 2^256-1.

Yesterday I thought .length = x was always O(1). That is why I was surprised and thought .length-- was different than .length = .length-1. Now I realize I was wrong in a different way.

I am working now to update the documentation. PR coming.

Here are the black box test cases:

pragma solidity ^0.4.23;

contract Array {
    uint[] public numbers;
    
    function length() external view returns (uint) {
        return numbers.length;
    }
    
    function numbers() external view returns (uint[]) {
        return numbers;
    }
    
    function inc() external {
        numbers.length++;
    }
    
    function dec() external {
        numbers.length--;
    }
    
    function plusOne() external {
        numbers.length = numbers.length + 1;
    }

    function plusALot() external {
        numbers.length = numbers.length + 2**20;
    }
    
    function minusOne() external {
        numbers.length = numbers.length - 1;
    }

    function minusALot() external {
        numbers.length = numbers.length - 2**20;
    }
    
    function pushOne() external {
        numbers.push(1);
    }
    
    function setSizeToTen() external {
        numbers.length = 10;
    }
    
    /*
    function pop() external {
        numbers.pop();
    }
    */
}

@fulldecent
Copy link
Contributor Author

Documentation fix added at be74b6d

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants