库合约与普通合约类似,但是它们只需要在特定的地址部署一次, 并且它们的代码可以通过 EVM 的 DELEGATECALL (Homestead 之前使用 CALLCODE 关键字)特性进行重用。
这意味着如果库函数被调用,它的代码在调用合约的上下文中执行, 即 this 指向调用合约,特别是可以访问调用合约的存储。
因为每个库合约都是一段独立的代码,所以它仅能访问调用合约明确提供的状态变量(否则它就无法通过名字访问这些变量)。
如果库函数不修改状态(也就是说,如果它们是 view 或者 pure 函数), 它们可以通过直接调用来使用(即不使用 DELEGATECALL 关键字), 这是因为我们假定库合约是无状态的。 特别的是,销毁一个库合约是不可能的。
库(Library)是一种特殊的合约,其主要目的是提供复用代码的功能。
库合约可以包含函数、事件、类型定义等,但与普通合约不同,库通常不持有状态(即不定义状态变量),也不能接收Ether。
库主要用于实现一些通用的、不依赖合约状态的函数,这些函数可以被其他合约调用。
类似于其他编程语言(如C++或Java)中的静态类,它们提供了一组静态方法,
这些方法可以在不同的 程序 中使用,而不需要每次都重新编写这些方法。
可以很好在促进代码重用、减少冗余,并提高智能合约开发的效率。
使用库的好处:
- 代码重用:库允许开发者将通用逻辑抽象出来,避免了代码的重复编写。
- 节省Gas:通过使用库中的函数,合约可以减少部署和执行的Gas成本,因为库代码在区块链上是单独部署的,并且可以被多个合约共享。
- 模块化:库可以帮助开发者构建更加模块化和可维护的代码基础。
注意事项:
- 库合约不能被继承或创建实例。
- 库函数通常被声明为
internal
,这意味着它们只能在合约内部或通过delegatecall
被调用。这是因为库代码被嵌入到调用它的合约中。 - 某些情况下可以使用
public
函数,但这将导致额外的Gas成本,因为它需要delegatecall
。
库合约是Solidity编程中一个非常强大的特性,它们能够帮助开发者写出更加高效、安全和模块化的智能合约代码。
库合约声明方式
声明一个库合约与声明普通合约类似,但使用 library 关键字代替了 contract 关键字。
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
library Test {
function add(uint256 a, uint256 b) internal pure returns (uint256) {
return a + b;
}
}