跳到主要内容

包初始化

init 函数的调用规则是什么?​

  • init: 包初始化时自动调用一次;
  • 调用限制: 不能被代码显式调用;
  • 使用位置: package 中可声明用于初始化的 init 函数;
package config

var Loaded bool

func init() {
Loaded = true
}
  • 声明限制: init 不接收参数、不返回值,同一个包甚至同一个文件可以声明多个 init;它们都由运行时初始化流程安排,而不是普通可调用函数值;

包初始化按什么依赖顺序执行?​

  • 多个 init: 按源码提交给编译器的文件顺序及文件内声明顺序执行;构建工具通常按文件名排序,不应把复杂业务依赖藏在文件名中;
  • 包变量依赖: 变量初始化会先满足同包变量依赖,不能简单理解为只按书写顺序执行;
阶段初始化对象
1被导入 package
2当前 package 变量
3当前 package 的 init
package config

var Limit = base + 1 // 依赖 base,先初始化 base
var base = 2

func init() {
println(Limit) // 3:包变量已经初始化完成
}
  • 生命周期: 包初始化在 main 之前完成;同一个被导入包只初始化一次,即使多个包都依赖它也不会重复执行 init;
  • 并发边界: 包初始化流程顺序调用 init,但 init 自己启动的 goroutine 可以并发运行,不应假定它在 main 开始前必然完成;