Arrays

如何拆分 56 個字元的輸入並將它們儲存在兩個 Bytes32 中?

  • August 22, 2017

我想要一個函式來接受、儲存和輸出 56 個字元。我的另一個問題(如何在 Solidity Contract 中返回字節數組)表明我試圖返回字節

$$ $$,但它給了我一個錯誤:

公共或外部函式不允許使用內部類型

我無法克服這個錯誤。

所以現在,我想看看能不能把輸入的56個字元拆分成兩個byte32,這樣就可以返回bytes32了。我該怎麼做呢?

我修改了這個問題的程式碼(如何將 Bytes32 源分成兩半並將它們儲存在 Bytes16 中?)並創建了這個:

 event trace(bytes x, bytes32 a, bytes32 b);

   function foo(bytes source) {
       bytes32[2] memory y = [bytes32(0), 0];
       assembly {
           mstore(y, source)
           mstore(add(y, 32), source)
       }
       trace(source, y[0], y[1]);
   }

 function cut(bytes sha) constant returns (bytes32 half1, bytes32 half2) {
   assembly {
     let freemem_pointer := mload(0x40)
     mstore(add(freemem_pointer,0x00), sha)
     half1 := mload(add(freemem_pointer,0x00))
     half2 := mload(add(freemem_pointer,0x10))
   }
 }

但我無法讓他們工作。

編輯於 2017-08-22 為 benjaminion:

理想情況下,我想返回字節

$$ $$. 查看我的程式碼和字節錯誤$$ $$在如何在 Solidity Contract 中返回字節數組。Benjaminion 的第一個程式碼塊進行了一些修改。我將“迭代器”函式更改為以下內容:

 function iterator() constant returns (address[],uint256[],uint256[],bytes32[],bytes32[]){
     uint256 len = ledger.keys.length;
     address[] memory keys = new address[](len);
     uint256[] memory values = new uint256[](len);
     uint256[] memory values2 = new uint256[](len);
     bytes32[] memory newKeys1 = new bytes32[](len);
     bytes32[] memory newKeys2 = new bytes32[](len);
     for (uint256 i = 0 ; i <  len ; i++) {
        address key = ledger.keys[i];
        keys[i] = key;
        values[i] = ledger.maps[key];
        values2[i] = token.balanceOf(key);

        bytes memory sha = ledger.newKeys[i];
        bytes32 half1;
        bytes32 half2;

        assembly {
           half1 := mload(add(sha,0x20))
           half2 := mload(add(sha,0x40))
        }
        newKeys1[i] = half1;
        newKeys2[i] = half2;
     }
     return (keys,values,values2,newKeys1,newKeys2);
 }

這應該可以實現您的問題:

contract Foo {
 function cut(bytes sha) constant returns (bytes32 half1, bytes32 half2) {
   assembly {
     half1 := mload(add(sha,0x20))
     half2 := mload(add(sha,0x40))
   }
 }
}

關鍵是該bytes數量sha包括 32 字節長度,後跟實際字節。所以我們跳過前 32 (= 0x20) 個字節來獲取half1,然後跳過另外 32 個字節來獲取half2

請注意,它sha是指向它所代表的數據開頭的指針,這就是我們可以這樣使用它的原因。


話雖如此,我不清楚為什麼你不能只做以下事情。bytes是完全允許的返回類型,可以有任意長度。

contract Foo {
 function foo(bytes sha) constant returns (bytes) {
   return sha;
 }
}

你可能真的想要這些方面的東西。

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