RE: RE: Solidity开发指南
You are viewing a single comment's thread from:

RE: Solidity开发指南

Words
116
Reading
1 min
Listen
Play
4M

call 会切换到被调合约中去执行方法,会切换上下文。msg.sender是主调合约地址。
delegatecall 则是将被调合约中的方法调到本合约中执行,也就是不会切换上下文。msg.sender是发起者本人。

另外,还有staticcall是 call 的只读版本,适用于调用不会修改状态的函数。在调用期间,合约的状态无法被改变。

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.20;

contract SetNum {
    uint256 public n = 20;
    address public sender;

    function setN(uint256 _n) public {
        n = _n;
        sender = msg.sender;
    }
}

contract CallSet {
    uint256 public n = 15;
    address public sender;

    function CallTest(address _addr, uint256 _n) public {
        _addr.call(abi.encodeWithSignature("setN(uint256)", _n));  //改变SetNum中的n值
        sender = msg.sender;  //是调用者本人,同时会改变SetNum的sender地址

        //(bool success, bytes memory returnData) = _addr.staticcall(data);
    }

    function delegatecallTest(address _addr, uint256 _n) public {
        _addr.delegatecall(abi.encodeWithSignature("setN(uint256)", _n)); //改变自身的n值
        //(bool success, bytes memory data) = _contract.delegatecall(
        //     abi.encodeWithSignature("setVars(uint256)", _num)
        // );
        sender = msg.sender;  //是调用者本人,不会改变SetNum的sender地址
    }
}

// 注意: delegatecall是相当于将被调合约的函数引入自身中执行,所以,这两个合约中的状态变量要一致!否则容易出错。
// 传入的参数(address _addr)是合约地址。