先说结合性
严格地讲 C 语言本身没有结合性(与优先级)的概念。它的语法是用 BNF (wiki)表示的。为了便于学习者理解,会提到左结合、右结合,但是它描述有些复杂的运算符的时候有些困难,比如 ?: 。
z = (a == b ? a : b ? c : d);
C 语言关于 ?: 的语法是这样定义的:
conditional-expression : logical-OR-expression ? expression : conditional-expression
? 前面是一个 "logical-OR-epxression",而 a==b ? a : b 不能解释为 "logical-OR-expression" 。所以,没有 () 的情况下,不会将 a==b ? a : b 结合在一起。
a = b = c
关于 "assignment expression" ,有如下规则:
assignment-expression : unary-expression assignment-operator assignment-expression
"assignment-operator" 左侧必须是一个 "unary-epxression" 。a 是 unary-expression ,但是 a = b 不是。所以必然后右侧的 b = c 结合为一个 "assignment-epxression" 。
所有的规则可以参考 C11标准草案 附录A 。
再说执行顺序
C 语言并不是先结合在一起的就会先执行的。
在同一个表达式内,除非有特殊规定,或者有依赖,否则求值顺序是不一定的。
对于
conditional-expression : logical-OR-expression `?` expression `:` conditional-expression
其中的 logical-OR-expression 一定是最先执行的。然后,根据其结果,选择 expression 与 conditional-epxression 之一执行。
在这里,
c == 0? printf("1\n"):(c=2)?(c = 3):printf("4\n")
c==0 先执行,然后(由于其结果是 true)执行 printf("1\n") 。
(c=2)?(c = 3):printf("4\n") 虽然被结合在了一起,但是作为外层 ?: 的一部分,根本没有执行。