solidity系列教程<九>库(library)的使用

2019-04-18  本文已影响0人  addin_gao

库与合约类似,它也部署在一个指定的地址上(仅被部署一次,当代码在不同的合约可反复使用)

因为库合约是一个独立的代码,它仅可以访问主调合约明确提供的状态变量,否则,没办法法去知道这些状态变量。

对比普通合约来说,库存在以下的限制(这些限制将来也可能在将来的版本被解除):

库有许多使用场景。两个主要的场景如下:

第一种使用库

pragma solidity ^0.4.16;

library Set {
  // 定义了一个结构体,保存主调函数的数据(本身并未实际存储的数据)。
  struct Data { mapping(uint => bool) flags; }

  // self是一个存储类型的引用(传入的会是一个引用,而不是拷贝的值),这是库函数的特点。
  // 参数名定为self 也是一个惯例,就像调用一个对象的方法一样.
  function insert(Data storage self, uint value)
      public
      returns (bool)
  {
      if (self.flags[value])
          return false; // 已存在
      self.flags[value] = true;
      return true;
  }

  function remove(Data storage self, uint value)
      public
      returns (bool)
  {
      if (!self.flags[value])
          return false; 
      self.flags[value] = false;
      return true;
  }

  function contains(Data storage self, uint value)
      public
      view
      returns (bool)
  {
      return self.flags[value];
  }
}

contract C {
    Set.Data knownValues;

    function register(uint value) public {
        // 库函数不需要实例化就可以调用,因为实例就是当前的合约
        require(Set.insert(knownValues, value));
    }
    // 在这个合约中,如果需要的话可以直接访问knownValues.flags,
}

using for:
指令using A for B;用来把库函数(从库A)关联到类型B。这些函数将会把调用函数的实例作为第一个参数。语法类似,python中的self变量一样。例如:A库有函数 add(B b1, B b2),则使用Using A for B指令后,如果有B b1就可以使用b1.add(b2)。

using A for * 表示库A中的函数可以关联到任意的类型上。

使用Using for的方式来对基本类型(elementary types)进行扩展:

pragma solidity ^0.4.16;

library Search {
    function indexOf(uint[] storage self, uint value)
        public
        view
        returns (uint)
    {
        for (uint i = 0; i < self.length; i++)
            if (self[i] == value) return i;
        return uint(-1);
    }
}

contract C {
    using Search for uint[];
    uint[] data;

    function append(uint value) public {
        data.push(value);
    }

    function replace(uint _old, uint _new) public {
        // 进行库调用
        uint index = data.indexOf(_old);
        if (index == uint(-1))
            data.push(_new);
        else
            data[index] = _new;
    }
}
上一篇 下一篇

猜你喜欢

热点阅读