Solidity

abi.encodePacked 有很多零

  • October 16, 2018

根據這個文件

短於 32 字節的類型既不是零填充也不是符號擴展,並且

當我使用 abi.encodePacked(address, uint, uint, address) 時,我得到一個包含很多零的結果。例如:

address addr = "0x14723A09ACff6D2A60DcdF7aA4AFf308FDDC160C";
uint x = 123;

abi.encodePacked(addr , x , x , addr)
0x14723a09acff6d2a60dcdf7aa4aff308fddc160c000000000000000000000000000000000000000000000000000000000000007b000000000000000000000000000000000000000000000000000000000000007b14723a09acff6d2a60dcdf7aa4aff308fddc160c

它不應該沒有零。

uint 是 256 位的,所以一切都正確編碼:

first parameter:  14723a09acff6d2a60dcdf7aa4aff308fddc160c
second parameter: 000000000000000000000000000000000000000000000000000000000000007b
third parameter:  000000000000000000000000000000000000000000000000000000000000007b
fourth parameter: 14723a09acff6d2a60dcdf7aa4aff308fddc160c

它不應該沒有零,它需要整個 32 個字節。

我知道你的困惑,你可能對函式“abi.encodePacked(…)”有一些誤解。

正如文件所說,“小於 32 字節的類型不填充零”,但您使用的類型是 uint,它恰好是 32 字節類型。

只需嘗試以下程式碼:

contract Test {

   function test() public pure returns (bytes memory, bytes memory) {
       int8 a = 1;
       uint16 b=2;
       return (abi.encode(a,b), abi.encodePacked(a,b));
   }
}

結果將是:

0x00000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000002

0x010002

請注意,我在此合約中使用 int8 和 uint16,因此不同之處在於“abi.encode”會將每個參數填充到 32 個字節,而“abi.encodePacked”不會。

引用自:https://ethereum.stackexchange.com/questions/59149