我很好奇某些各种类型的表达式的顺序,所以我在顶级声明级别尝试了这个代码,认为它会失败,但发现它有效:
http://play.golang.org/p/CfP3DEC5LP
var x = func() *Foo {
fmt.Println(f) // prints &{foobar}
return f
}()
var f = &Foo{"foobar"}
type Foo struct {
bar string
}
请注意:
type Foo struct
声明位于底部
type
声明之前有一个var f
声明和&Foo{]
作业
在var
声明之前,有一个立即调用的函数,它引用并返回f
变量。
虽然在&Foo{}
声明之前发生了type Foo struct
值,但我并没有让我感到惊讶,但我确实能够成功引用并打印{分配前的{1}}值。
这是一种可靠且明确的行为吗?我在规范中找不到任何对这种排序的引用,但也许我忽略了它。
答案 0 :(得分:10)
请参阅the Go programming language reference
在包中,初始化包级变量,和 根据参考顺序确定常数值:if A的初始化程序取决于B,A将在B. Dependency之后设置 分析不依赖于项目的实际值 初始化,仅限于它们在源头中的外观。 A取决于B if A的值包含B的提及,包含一个值 初始化程序提到B,或者提到一个提到B的函数, 递归。如果这种依赖性形成一个循环,那就是错误。如果两个 项目不是相互依赖的,它们将在订单中初始化 它们出现在源中,可能出现在多个文件中 编译器。由于每个包都进行了依赖性分析 如果A的初始化程序调用函数,则会产生未指定的结果 在另一个引用B的包中定义。