我正在收到以下错误:
Type bytes32[] memory is not implicitly convertible to expected type bytes32[] storage pointer.
当解压应该是bytes32的内容时,即a in Problem结构(1)。
//FileOne.sol
contract ExampleOne {
struct Problem {
bytes32 a; // (1)
bytes32 b;
bytes32[] c;
uint d;
}
mapping (bytes32 => Problem) public problems;
}
//FileTwo.sol
contract IExampleOne {
function problems(bytes32) public returns (bytes32, bytes32, bytes32[], uint);
}
contract Example Two {
IExampleOne exampleOne;
constructor(address _exampleOne) {
exampleOne = IExampleOne(_exampleOne);
}
function func(bytes32 name) {
(bytes32 a, bytes32 b, bytes32[] c, uint d) = problems(name); //ERROR
...
}
}发布于 2018-11-15 23:32:01
好消息。它只需做一些调整就可以编译。
坏消息。这对气体来说是很困难的,并且取决于所传递的数组的长度,当接口中涉及到数组时,这可能太昂贵了而不是实际的--标准的警告。
作为另一种选择,您可以为标量值(return (p.a, p.b, p.d))和数组(return p.c[row];)中的各个行创建getter。这样做将确保单独调用费用相同,并节省天然气。
要编译代码,诀窍是将c[]转换为memory指针。这相当于通过ABI从其他合同收到的数据(即不来自存储)。默认情况下,它是一个存储指针。
//FileOne.sol
contract ExampleOne {
struct Problem {
bytes32 a; // (1)
bytes32 b;
bytes32[] c;
uint d;
}
mapping (bytes32 => Problem) public problems;
}
//FileTwo.sol
contract IExampleOne {
function problems(bytes32) public returns (bytes32, bytes32, bytes32[], uint);
}
contract ExampleTwo {
IExampleOne exampleOne;
constructor(address _exampleOne) {
exampleOne = IExampleOne(_exampleOne);
}
function func(bytes32 name) {
(bytes32 a, bytes32 b, bytes32[] memory c, uint d) = exampleOne.problems(name); // NO ERROR
//...
}
}如果对可伸缩性的评论有兴趣的话,那么担心的是,双方都需要越来越多的气体来打包和解压越来越大的列表。您的ExampleOne可以提供潜力,以任何规模阅读它使用许多小电话,而不是一个大的。
function getProblemMeta(bytes32 problemId) public view returns(bytes32, bytes32, uint) {
p = problems[problemId];
return (p.a, p.b, p.d);
}
function getProblemCAtIndex(bytes32 problemId, uint index) public view returns(bytes32) {
return problems[problemId].c[index];
}希望能帮上忙。
https://ethereum.stackexchange.com/questions/62430
复制相似问题