Sur*_*hli 5 data-structures solidity
我已经使用solidity将数据推送到数组中.pop有类似的功能吗?
string[] myArray;
myArray.push("hello")
Run Code Online (Sandbox Code Playgroud)
什么是最好的解决方案?如何在稳定性中删除动态数组中的元素?
更新2-19-2019:正如Joel在下面指出的那样,pop
已添加到内置阵列支持中.请参阅https://solidity.readthedocs.io/en/v0.5.4/types.html#array-members.留下原始答案,以防其他人使用旧版本的Solidity.
Solidity中没有pop功能.您可以考虑使用几个选项来维护阵列.
删除并留下空白
最简单的解决方案是仅delete
使用特定索引处的元素:
string element = myArray[index];
delete myArray[index];
return element;
Run Code Online (Sandbox Code Playgroud)
但是,这不会移动数组中的元素,并且会在数组中留下"string 0"元素.要检查此元素,您可以使用
if(bytes(myArray[index]).length > 0) ...
交换和删除
如果您不关心数组中的顺序,可以将元素与数组中的最后一个元素交换,然后删除:
string element = myArray[index];
myArray[index] = myArray[myArray.length - 1];
delete myArray[myArray.length - 1];
myArray.length--;
return element;
Run Code Online (Sandbox Code Playgroud)
使用Shift删除
如果数组中的顺序很重要,则可以删除该元素,然后将所有剩余元素移到左侧.
string element = myArray[index];
for (uint i = index; i < myArray.length - 1; i++) {
myArray[index] = myArray[index + 1];
}
delete myArray[myArray.length - 1];
myArray.length--;
return element;
Run Code Online (Sandbox Code Playgroud)
请注意,这将是最昂贵的选项.如果您的阵列很长,您的天然气使用量很高.
与@ Jedsada的建议相关,这是一个作为库的版本:
pragma solidity ^0.4.24;
library StackLib {
using StackLib for Stack;
struct Stack {
uint[] _items;
}
function pushElement(Stack storage self, uint element) internal returns (bool) {
self._items.push(element);
}
function popElement(Stack storage self) internal returns (uint) {
uint element = self.peek();
if (self.size() > 0)
delete self._items[self.size() - 1];
return element;
}
function peek(Stack storage self) internal returns (uint) {
uint value;
if (self.size() > 0)
value = self._items[self.size() - 1];
return value;
}
function size(Stack storage self) internal returns (uint8) {
return self.size();
}
}
Run Code Online (Sandbox Code Playgroud)
示例用法(重要说明:您不能使用popElement
并将值返回给客户端.该方法更改状态,只应在事务中使用.):
contract Test {
using StackLib for StackLib.Stack;
StackLib.Stack numbers;
function add(uint v) public {
numbers.pushElement(v);
}
function doSomething() public {
for (uint8 i = 0; i < numbers.size(); i++) {
uint curNum = numbers.popElement();
// do something with curNum
}
}
}
Run Code Online (Sandbox Code Playgroud)
附加说明:遗憾的是,var
自0.4.20以来已被弃用,并且没有替代泛型.您必须为特定类型进行自定义.