Go:关于多个作业的混淆

时间:2018-02-03 12:04:55

标签: go

我对Go中的多个作业感到有点困惑,例如varA, varB = varC, varD

我的问题是,这样的操作是原子的(当然不是在HW层,而是从程序员的角度来看)?

就我个人而言,我希望它是原子的,所以这个表达式a, b = b, a只是交换值。我在Go playground中尝试了它,是的,它的确如此。

另一方面,Golang specs州:

  

转让分两个阶段进行。首先,左侧的索引表达式和指针间接操作(包括选择器中的隐式指针间接)的操作数和右侧的表达式都按通常的顺序进行评估。 其次,分配按从左到右的顺序进行。

我理解为a被赋予b的值,然后b被赋予a的值(现在为b),最后,ab都等于b的原始值。

规格是错误的还是我误解了?

1 个答案:

答案 0 :(得分:5)

你误解了它,这不是你误解的第二部分。

规范说:

  

首先,左边的索引表达式和指针间接操作(包括选择器中的隐式指针间接)的操作数和右边的表达式都按照通常的顺序评估

这里评估意味着所有表达式,包括变量都是......,好吧,被评估为值,并且该值在那时是固定的。所以在a,b = b,a中,在第一部分中,lhs表达式a,b得到了解析,rhs表达式b,a被评估为5,3(假设a,b:=3,5,当然);在第二部分,作业发生了,变成了a = 5; b = 3

使用defer和goroutine时,评估是一样的。这就是为什么以下代码打印5。

func T() {
    x := 5
    defer func(i int) {
        fmt.Println(i)
    }(x)
    x = 3
}