Storage
警告:未初始化的儲存指針
我正在嘗試計算嬰兒步巨步算法以找到離散對數。但是由於警告,我無法編譯程式碼。它出現在 uint256[] storage A 和 uint256[] storage B
這是程式碼:
function squareRoot(uint256 x) public returns (uint256 y) { uint256 z = (x + 1) / 2; y = x; while (z < y) { y = z; z = (x / z + z) / 2; } } function ceiling(uint256 a) constant returns (uint256) { return (a / 1) * 1; } function proofOfWorkOptimized() onlyOwner public { uint256 base = 19; uint256 exponent; uint256 modulo = 221; uint256 valueAtIndexi; uint256 valueAtIndexj; uint256 rootCeiling = ceiling(squareRoot(modulo)); uint256[] storage A; uint256[] storage B; for (uint256 i = 1; i <= rootCeiling; i++){ uint256 result = base**i % modulo; A.push(result); } for (uint256 j = 0; j < rootCeiling; j++){ result = base**(rootCeiling*j) % modulo; B.push(result); } for (i = 1; i <= A.length-1; i++){ for (j = 1; j <= B.length-1; j++){ if (i == j){ valueAtIndexi = A[i]; valueAtIndexj = B[j]; break; } } } exponent = ((valueAtIndexj + 1)*rootCeiling - valueAtIndexi) % modulo;
我該如何解決?
這有點棘手。除非您有真正的理由不這樣做,否則您應該將
A
and聲明B
為記憶體,而不是儲存。就目前而言,您的程式碼向儲存寫入 28 次,這將花費 28 * 20,000 = 560,000 氣體,這是一筆巨款。將數組放在記憶體中會大大提高效率。如此聲明 A 和 B :
uint256[] memory A = new uint256[](rootCeiling); uint256[] memory B = new uint256[](rootCeiling);
要將 A 和 B 作為記憶體數組寫入,您不能使用
push
. 只需這樣做:A[i-1] = result; .... B[j] = result;
順便說一句,嵌套循環不使用
[0]
數組的索引。如果正確,您可能不需要計算它們。免責聲明:以上內容未經測試(但可以編譯),因此 E&OE。
PS如果您真的想要
A
並且B
要儲存,只需將函式範圍之外的聲明移動到合同的主體中並刪除storage
聲明(這是隱含的):Contract Foo { uint256[] A; uint256[] B; ...