它是C语句的声明和初始化语句中的逗号运算符吗?

时间:2016-09-10 23:14:38

标签: c comma-operator

我正在阅读C编程语言并找到了这句话:

  

在声明中分隔...变量的逗号...不是逗号运算符,也不保证从左到右的评估。

如果是这样,他们是否在此代码中使用逗号运算符?

int a=1, b=a+1, c=b+a+1, d=c+b+a+1;

我很确定它会起作用。但如果他们不是逗号操作符并且不保证从左到右的顺序,则上述语句可能会失败,对吗?

2 个答案:

答案 0 :(得分:8)

声明中的逗号不是表达式中的逗号运算符(声明不是表达式,尽管声明中的初始化是表达式)。如果单独声明的逗号不是逗号运算符,则问题中的引用是准确的。

但是,每个声明符都以其后面的逗号或分号完成,因此问题中的变量定义是完全定义的行为。当它暗示从无法保证从左到右的评价时,引用是不正确的 - 虽然它是一个精巧的语言剖析。如果逗号是逗号运算符,则该事实将保证从左到右的评估;因为它们不是逗号运算符,所以从左到右的保证不会出现在逗号运算符的定义中。但是,因为每个声明符后都有序列点,所以从左到右的估值是单独保证的。

在标准中找到合适的措辞来证明这种说法比我预期的要困难。它实际上在关于声明者的部分。

  

§6.7声明

     

<强>语法

     

声明:
   declaration-specifiers init-declarator-list opt ;
  ...

     

...

     

初始化声明符列表:
  初始化声明符
   init-declarator-list,init-declarator

     

初始化声明符:
  声明符
  声明者 = 初始值设定项

     

¶6声明说明符由一系列说明符组成,这些说明符指示声明符所表示的实体的链接,存储持续时间和部分类型。 init-declarator-list是一个以逗号分隔的声明符序列,每个声明符都可以包含其他类型信息,或初始值设定项,或两者兼而有之。声明符包含声明的标识符(如果有)。

     

¶7如果声明对象的标识符没有链接,则对象的类型应在其声明符的末尾完成,或者如果它具有初始化器,则在其init-declarator的末尾完成;在函数参数(包括原型)的情况下,它是经过调整的   类型(见6.7.6.3),需要完整。

     

§6.7.6声明者

     

¶3完整声明符是一个不属于另一个声明符的声明符。完整声明符的结尾是一个序列点。

AFAICS,§6.7.9初始化程序不会添加任何相关内容。

序列点至关重要;这意味着在继续之前,左边的所有内容都得到了充分评估,副作用已经完成;它意味着从左到右的排序,因此问题中的初始化是完全定义的。

序列点在完整的声明符之后,而不是初始化器,这有点奇怪;不过,我认为这不重要。

答案 1 :(得分:0)

不,它可能不会,因为在声明中逗号充当序列点,保证将按照上述顺序执行评估。 您可以在此处找到更多信息:Sequence point