2 回答
TA贡献1815条经验 获得超13个赞
您正在块中创建foo一个if 新 变量:=
foo, found := os.LookupEnv("GOPATH")
检查块和范围规则。
正确的代码:
package main
import (
"fmt"
"os"
)
func main() {
var foo string
var found bool
if true {
foo = "foo"
} else {
foo, found = os.LookupEnv("GOPATH")
if !found {
fmt.Printf("who cares.\n")
}
}
println(foo)
}
TA贡献1757条经验 获得超7个赞
来自 Go 文档:
在块中声明的标识符可以在内部块中重新声明。虽然内部声明的标识符在范围内,但它表示由内部声明声明的实体。
:= 在 else 块中重新声明了 foo,因此 foo 现在指的是一个全新的同名变量,一个从未使用过的变量。即使我们以某种方式到达 else 块,最后一行的 println(foo) 也不会打印我们的 $GOPATH,因为它存储在另一个 foo 变量中(或者直到整个变量超出范围)
正确的代码是:
func main() {
var foo string
if true {
foo = "foo"
} else {
var found bool
foo, found = os.LookupEnv("GOPATH")
if !found {
fmt.Printf("who cares.\n")
}
}
println(foo)
}
很容易混淆,因为即使 foo 在使用之前重新声明,这段代码也能正常工作:
func main() {
var foo string
foo = "foo"
foo, found := os.LookupEnv("GOPATH")
if !found {
fmt.Printf("who cares.\n")
}
println(foo)
}
这里发生的是,Go 中还有另一种不同类型的合法重新声明:
与常规变量声明不同,短变量声明可以重新声明变量,前提是它们最初是在同一块(或参数列表,如果该块是函数体)中以相同类型声明的,并且至少有一个非空白变量是新的。因此,重新声明只能出现在多变量短声明中。重新声明不引入新变量;它只是为原始值分配一个新值。
所以在另一种类型的重新声明中,实际上并没有创建新的 foo 变量,它的工作方式就像对 foo 的赋值。
- 2 回答
- 0 关注
- 178 浏览
添加回答
举报