Передавать функцию в качестве параметра в Solidity

Можете ли вы передать функцию в качестве параметра в Solidity?

Мое предположение: В Solidity существует концепция address, но они представляют contract s. Контракты могут иметь резервные функции, но я не думаю, что вы можете дать им параметры. Думая о передаче функции в качестве параметра по адресу, подобному тому, который вы делаете в C.

Есть ли законный способ передать функции в качестве параметров, или если нет, есть ли взломанный способ?

Если есть, как? А если нет, то почему?

18 голосов | спросил Karl Floersch 25 PMpMon, 25 Apr 2016 18:52:23 +030052Monday 2016, 18:52:23

3 ответа


14

Функции (аналогичные методы) указаны в ABI и имеют идентификатор метода, который является первым 4 байта sha3 (Keccak-256) подписи метода.

Вот пример вызова someFunction в contract: contract.call(bytes4(sha3("someFunction()")))

Вот проверенная функция с передачей methodId в качестве параметра:

contract C1 {
    uint public _n;  // public just for easy inspection in Solidity Browser

    function foo(uint n) returns(uint) {
        _n = n;
        return _n;
    }

    function invoke(bytes4 methodId, uint n) returns(bool) {
        return this.call(methodId, n);
    }
}

Протестируйте его в браузере Solidity с помощью "0x2fbebd38", 9 в качестве параметры invoke, а затем посмотрите, что _n равно 9.

Примечания:

  • 0x2fbebd38 является результатом bytes4(sha3("foo(uint256)")) (не забывайте о необходимости использовать канонические типы, в этот случай uint256, на ABI. )

  •   

    Возвращаемые значения из вызова и код вызова являются логическими, либо вызов   или вызов завершился неудачно. Невозможно вернуть значение   от вызова, поскольку для этого потребуется, чтобы контракт знал о возврате   типа заранее.

ответил eth 26 PMpTue, 26 Apr 2016 12:33:57 +030033Tuesday 2016, 12:33:57
6

Ответ eth применяется к внешним вызовам функций (между контрактами или с использованием внешнего интерфейса для вызова вашего собственного контракта); здесь я попытаюсь ответить на вызовы внутренних функций.

В настоящее время Solidity не содержит синтаксиса для описания типа указателя функции, поэтому вы не можете воспринимать их как аргументы или возвращаемые значения. Однако функции являются первоклассными и могут быть назначены переменным с помощью var; вот пример из руководства пользователя Solidity :

contract FunctionSelector {
  function select(bool useB, uint x) returns (uint z) {
    var f = a;
    if (useB) f = b;
    return f(x);
  }
  function a(uint x) returns (uint z) {
    return x * x;
  }
  function b(uint x) returns (uint z) {
    return 2 * x;
  }
}
ответил Nick Johnson 26 PMpTue, 26 Apr 2016 17:18:51 +030018Tuesday 2016, 17:18:51
5

Чтобы добавить ответ Ник Джонсон, типы функций в последних версиях прочности позволяют вам теперь описывать указатели на функции:

http://solidity.readthedocs.io/en/latest/types.html # функция-типа

  

Типы функций - это типы функций. Переменные типа функции могут быть назначены из функций, а функциональные параметры типа функции могут использоваться для передачи функций и возврата функций из вызовов функций. Типы функций представлены в двух вариантах: внутренние и внешние функции

ответил Michael 9 Mayam17 2017, 04:31:09

Похожие вопросы

Популярные теги

security × 330linux × 316macos × 2827 × 268performance × 244command-line × 241sql-server × 235joomla-3.x × 222java × 189c++ × 186windows × 180cisco × 168bash × 158c# × 142gmail × 139arduino-uno × 139javascript × 134ssh × 133seo × 132mysql × 132