基于 bytes4 函数选择器动态调用 Solidity 函数

bgu*_*uiz 8 blockchain ethereum solidity smartcontracts rsk

在智能合约中,假设我有一个函数想要根据某些内部逻辑动态调用另一个函数。这里它获取函数选择器作为bytes4变量。

之后就可以使用分支逻辑来调用目标函数之一。看到

但是,是否可以避免这种情况并直接调用函数选择器?参见:(B)

function myDynamicFunc(uint256 someParam) public {
    bytes4 selector = /* ... some internal logic ... */

    if (selector == this.myFuncA.selector) {
      myFuncA(someParam);
    } else if (selector == this.myFuncB.selector) {
      myFuncB(someParam);
    }
    // (A) instead of something like this ^ branching logic (which works)

    selector.invoke(someParam);
    // (B) can something like this ^ instead by calling the selector directly instead (does not work)
}

Run Code Online (Sandbox Code Playgroud)

细节

  • myDynamicFuncpublicmyFuncA+myFuncB也是public
  • 所有 3 个功能都在同一个智能合约中实现。

笔记

我已经写了一个答案,扩展了@kj-crypto评论中的建议。如果有另一种方法可以在不使用的情况下完成上述任务address(this).call(...),我洗耳恭听!

dev*_*per 6

关于B选项:

  • 使用call将返回一个字节对象,然后您应该将其转换为适当的类型,在本例中为整数。(额外的气体使用量)
  • 使用时call需要打包选择器和参数(额外使用gas)

只要您在同一个合约中使用某个函数,就没有必要使用它的 abi 规范,因为您现在已经知道该函数在哪里,它是如何定义的,并且您可以毫无麻烦地调用它。