Go中比较运算符优先级高于位运算符和逻辑运算符,故a & b == c被解析为a & (b == c)导致类型错误;混合运算必须加括号,如(flags & mask) != 0;&&优先级高于||,且均支持短路求值。

&& 和 || 优先级低于比较运算符,写条件时漏括号极易导致语义错误——这不是风格问题,是编译器按规则解析的必然结果。
为什么 a & b == c 不等于 (a & b) == c
Go 把 a & b == c 解析为 a & (b == c),因为 == 优先级高于 &。而 b == c 返回 bool,a & bool 直接编译报错:invalid operation: a & (b == c) (mismatched types int and bool)。
- 这种错误在位掩码校验中高频出现,比如想判断
flags & READ_FLAG != 0,漏括号就成flags & (READ_FLAG != 0),类型不匹配 -
==、!=、、<code>>等比较运算符统一高于所有位运算符(&、|、^、&^) - 唯一安全做法:凡涉及位运算与比较混合,一律加括号,如
(flags & mask) != 0
&& 和 || 的结合顺序与短路行为
&& 优先级高于 ||,所以 a || b && c 等价于 a || (b && c),不是 (a || b) && c。这点和数学中“先乘除后加减”逻辑一致,但容易被直觉误导。
-
&&短路:左侧为false时,右侧表达式完全不执行(可用于避免空指针或昂贵计算) -
||短路:左侧为true时,右侧跳过 - 组合多个条件时,别依赖默认优先级,例如
age >= 16 && hasConsent || age >= 18语义模糊,应写成(age >= 16 && hasConsent) || age >= 18
算术、位移、比较三类运算符的层级陷阱
和 <code>>> 优先级比 +、- 还低,这是最反直觉的一点。例如 val 实际执行的是 <code>val ,而非 <code>(val 。
使用 uber-go/dig 在 Golang 中实现依赖注入——基于反射容器,提供 Provide/Invoke、dig.In/dig.Out 参数与结果对象,支持命名依赖等
- 常见误用场景:指针偏移计算
base + offset → 必须写成 <code>base + (offset -
^是异或,不是幂运算;Go 没有**,算幂得用math.Pow或位移技巧 - 所有二元算术/位运算符(
+、-、&、|、^)都是左结合,但优先级跨层明显,不能靠“从左到右”猜顺序
复合赋值运算符的括号保障机制
a += b & c 等效于 a = a + (b & c),不是 (a + b) & c。Go 规定所有复合赋值(+=、&=、^= 等)自动将右侧整个表达式括起来代入。
立即学习“go语言免费学习笔记(深入)”;
- 这比 C 安全,但容易让人误以为“右边会先整体求值”,其实只是语法糖保证了括号包裹
- 仍需警惕混合类型:例如
a &= b == c展开为a = a & (b == c),b == c是bool,与a(假设是int)做&仍会编译失败 - 真正需要手动加括号的地方,永远是「跨优先级层级」的组合,比如位运算+比较、位移+加减、逻辑+比较
if x&y == 0 看着像位掩码判零,实则先算 y == 0 再与 x 按位与,类型都对不上。

















