Go 的并行赋值(如 a, b = b, a+b)在执行时会先求值所有右侧表达式,再统一赋值给左侧变量;而逐个赋值则按顺序执行,后一条语句会立即影响前一条语句中已修改的变量值。这是二者行为差异的根本原因。
go 的并行赋值(如 `a, b = b, a+b`)在执行时会**先求值所有右侧表达式,再统一赋值给左侧变量**;而逐个赋值则按顺序执行,后一条语句会立即影响前一条语句中已修改的变量值。这是二者行为差异的根本原因。
在 Go 中,多变量并行赋值(也称“同时赋值”或“元组赋值”)是一个原子性操作:所有右侧表达式会在任何左侧变量被修改之前完成求值,然后一次性将结果写入对应变量。这种设计避免了依赖赋值顺序带来的歧义,尤其在变量间存在数据依赖时至关重要。
以原题中的函数 b() 为例:
z, x, y = x, y, x+y // 并行赋值
执行过程为:
- 先计算右侧所有值:此时 x == 1, y == 2,因此右侧表达式结果为 (1, 2, 1+2) → (1, 2, 3);
- 再统一赋值:z = 1,x = 2,y = 3。
最终返回 (x, y, z) = (2, 3, 1),与运行结果一致。
而函数 a() 是顺序赋值:
z = x // z ← 1(此时 x=1, y=2) x = y // x ← 2(x 已更新为 2) y = x + y // y ← 2 + 2 = 4(注意:此处 x 已是新值!)
关键区别在于第三步:y = x + y 中的 x 是第二步刚更新后的值(2),而非原始值(1),因此结果为 y = 4,最终返回 (2, 4, 1)。
✅ 正确理解要点:
- 并行赋值 = “快照式”求值(右侧全部冻结后再写入);
- 顺序赋值 = “流水线式”执行(每步立即生效,后续步骤可见变更);
- 并行赋值天然支持无临时变量交换(如 a, b = b, a)和安全的依赖更新(如斐波那契迭代 a, b = b, a+b)。
⚠️ 注意事项:
- 不要误以为 a, b = b, a+b 等价于 a = b; b = a+b —— 后者会因 a 提前被覆盖而破坏原始 a 值;
- 所有右侧表达式按从左到右顺序求值,但求值结果在赋值前已全部确定;
- 若右侧包含函数调用(如 x, y = f(), g()),它们仍会全部执行完毕后再赋值,且 f() 和 g() 的执行顺序是确定的(左优先)。
这种设计使 Go 的并发赋值既简洁又可预测,是编写清晰、健壮数值逻辑(如状态机、迭代算法、坐标变换)的重要基础。


















