2012-07-08 169 views
15

从我规范的阅读:Go中短变量声明和长变量声明之间的关闭范围区别是什么?

短变量声明...是一个常规变量 声明与初始化表达式,但没有一个类型速记......

http://golang.org/ref/spec

我原以为两者是相同的:

var f func() 
f = func() { 
    ... 
} 

f := func() { 
    ... 
} 

但似乎他们不是。我试图总结外函数内自递归函数,但这个工程:

func myOuter() { 
    var f func() 

    f = func() { 
     f() 
    } 

    f() 
} 

但是这不,说在内部函数undefined: f

func myOuter() { 
    f := func() { 
     f() 
    } 

    f() 
} 

那么有什么区别? 有没有什么办法可以用短格式声明来写这个或者我必须把它写出来?

+0

谢谢Kissaki,我明显粘贴了两次错误的相同的东西。 – Joe 2012-07-08 13:25:17

回答

14

f := func() { /* ... */ }var f func() = func() { /* ... */ }完全相同(但只有后者才允许在包级别)。在您的具体情况下,两种变体都不会起作用,因为声明将从右向左进行评估。解决办法是 - 如您已经建议的 - 将声明分成两部分。一个用于声明变量,另一个用于赋予递归函数。

+1

谢谢!我的订单或声明没有发生。 – Joe 2012-07-08 12:42:04

+0

啊!现在我必须再次解除我的代码,谢谢你的洞察! – 2014-02-24 21:02:02

0

在一个条件下,您的前两个代码示例在语义上是相同的:正在分配给您的变量的表达式需要在编译时解析。

除了当您试图分配引用您刚刚声明的变量(或函数)的表达式时,这在每种情况下都是相同的。这里的问题在于,因为golang是以右关联的方式解析的,所以它会尝试在将它分配给左边之前,在右边键入解析表达式。如果引用declare-assign运算符左侧的变量,则引用编译器尚不知道的变量,因此undefined: f

,将产生类似的结果又如:

x := x + 1 

虽然这是很不常见的人尝试,因为它是更明显的是,X尚未分配。