Solidity - 合约升级

目录

合约调用

智能合约升级

1、主-从模式

2、代理模式


 

合约调用

以下是一个合约调用另一个合约示例:

pragma solidity^0.6.0;

contract C1{
    string private name;

    function getName() external view returns (string memory) {
        return name;
    }

    function setName(string calldata _name) external {
        name = _name;
    }
}

contract C2{
    C1 c;

    constructor(address addr) public {
        //部署时填写被调用合约C1的地址
        c = C1(addr);
    }

    function getName() external view returns (string memory) {
        return c.getName();
    }

    function setName(string calldata _name) external {
        c.setName(_name);
    }
}

引用被调用合约的地址:

    constructor(address addr) public {
        c = C1(addr);  //部署时填写被调用合约C1的地址
    }

部署如下图所示: 

智能合约升级

1、主-从模式

主合约地址永恒不变

从合约地址可以更改或设置多个 

从合约地址可以通过主合约地址获取 

合约部署后会生成一个合约地址,一个合约多次部署会生成不同的合约地址,不同的合约地址对应的是不同的实例,如果想调用一个合约,必须知道合约地址,还需要知道合约的ABI。主合约知道从合约地址与从合约ABI就可以进行调用了。如下示例:

pragma solidity^0.6.0;

//接囗IC
interface IC {
    //获取名称
    function getName() external view returns(string memory);
    //设置名称
    function setName(string calldata _name) external;

}

//合约C1实现接囗IC
contract C1 is IC {
    //状态变量
    string name;

    //获取名称
    function getName() external view override returns(string memory){
        return name;
    }
    //设置名称
    function setName(string calldata _name) external override{
        name = _name;
    }
}

//合约C2实现接囗IC
contract C2 is IC {
    //状态变量
    string name;

    //获取名称
    function getName() external view override returns(string memory){
        return name;
    }
    //设置名称
    function setName(string calldata _name) external override{
        name = _name;
    }
}

//合约C通过合约地址调用C1或C2
contract C {
    //状态变量,接囗IC
    IC c;

    //设置合约地址
    function setICAddress(address addr) public {
        c = IC(addr);
    }

    //通过接囗调用 获取名称
    function getName() public view returns (string memory) {
        return c.getName();
    }

    //通过接囗调用 设置名称
    function setName(string memory _name) public {
        c.setName(_name);
    }
}

2、代理模式

代理模式借鉴的是回调思想,只关注合约地址,并不关注合约的ABI。

合约想要收取外部账户给的以太(钱)时,要使用fallbak或receive。

未使用fallbak或receive时,合约接收钱,如下例代码所示:

pragma solidity^0.6.0;

contract C1{
    function getContractAccountBalance() public view returns (uint256) {
        return address(this).balance;
    }
}

contract C{
    function transfer(address payable _to, uint256 _value) public payable{
        require(msg.value >= _value, "转账金额要充足");
        _to.transfer(_value);
    }
}

部署后,运行结果如下图所示: 

合约C1中增加fallback或receive,表示能够接收外部账户转账的钱,代码如下:

pragma solidity^0.6.0;

contract C1{
    function getContractAccountBalance() public view returns (uint256) {
        return address(this).balance;
    }

    //fallback表示此合约能够接收外部账户转账的钱
    fallback() external payable {

    }
}

contract C{
    function transfer(address payable _to, uint256 _value) public payable{
        require(msg.value >= _value, "转账金额要充足");
        _to.transfer(_value);
    }
}

 部署后,运行结果如下图所示: 

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Solidity中,可以通过使用智能合约来实现ERC20代币的锁仓与释放。以下是一个简单的锁仓合约示例: ``` pragma solidity ^0.8.0; import "./IERC20.sol"; import "./SafeMath.sol"; contract TokenVesting { using SafeMath for uint256; address public beneficiary; uint256 public cliff; uint256 public start; uint256 public duration; uint256 public released; IERC20 public token; constructor( address _beneficiary, uint256 _cliff, uint256 _duration, address _token ) public { require(_beneficiary != address(0)); require(_cliff <= _duration); beneficiary = _beneficiary; cliff = _cliff; duration = _duration; start = block.timestamp; token = IERC20(_token); } function release() public { uint256 unreleased = releasableAmount(); require(unreleased > 0); released = released.add(unreleased); token.transfer(beneficiary, unreleased); } function releasableAmount() public view returns (uint256) { return vestedAmount().sub(released); } function vestedAmount() public view returns (uint256) { uint256 currentBalance = token.balanceOf(address(this)); uint256 totalBalance = currentBalance.add(released); if (block.timestamp < start.add(cliff)) { return 0; } else if (block.timestamp >= start.add(duration)) { return totalBalance; } else { return totalBalance.mul(block.timestamp.sub(start)).div(duration); } } } ``` 在这个合约中,当创建合约时,需要传入受益人地址、锁仓期、释放期、代币地址等信息。锁仓期结束后,受益人可以通过调用 `release()` 函数来释放锁仓代币。如果释放函数被调用,但是当前时间还没有到达释放期,则会抛出异常。 为了保证代币不能被提前释放,合约还实现了 cliff 的概念,即在锁仓期结束之前,代币不能被释放。当 cliff 结束之后,代币将按照线性方式释放,直到释放期结束。 需要注意的是,以上示例只是一个简单的锁仓合约示例,实际生产环境中需要更加严格地考虑各种情况和安全性问题。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值