变量1 =({statement 1; statement 2;})在C中构造

时间:2014-09-02 04:46:17

标签: c gcc

main()

{

       int a=10,b=30,c=0;

       if( c =({a+b;b-a;})) 
       {
          printf("%d",c);
       }

}

为什么构造({;})在C中是合法的,为什么它返回最后一个语句值作为表达式的结果(为什么它与逗号运算符类似)?

2 个答案:

答案 0 :(得分:15)

它不是合法标准C99,但它是一个非常有用的GCC扩展名,称为statement-exprs(带括号的大括号复合语句,以某个表达式结尾)。

IIRC,其他一些编译器支持该扩展,例如Clang/LLVM

语句表达式在包含控制流更改和副作用时非常有用,例如:

 c = 2*({while (a>0) a--,b--; a+b;});

但是,在您的特定情况下,您可以使用comma operator

 if (c=(a+b,b-a))

由于a+b没有任何副作用,我想优化编译器可以将其作为

处理
 if (c=b-a)

GCC提供了其他有用的extensions,特别是local labels使用__label__label as values计算得到的(在threaded interpreters ...中非常有用)。我不确切地知道为什么他们没有被标准化。我希望他们愿意。

答案 1 :(得分:1)

main()
  {

   int a=10,b=30,c=0;

   if( c =({a+b;b-a;})) 
   {
      printf("%d",c);
   }

  }

在这里,{a+b;b-a;}是一个范围。在这里你写了2个语句。这实际上被视为

   {
    c=a+b;
    c=b-a;
   }

由于a+b,最初c值为40。同样c由b-a修改。为了证明这一点,请考虑以下三种情况。

(1)。

 if(c=({(a=a+b);;}))
   {
      printf("%d\n",c);
      printf("%d\n",a);
   }

这里o / p是c = 40和a = 40;因为在范围的末尾(即)在最后一个语句中是虚拟(;)。 所以,c=a+b是o / p。 (2)

   if(c=({(a=a+b);b-a;}))
   {
      printf("%d\n",c);
      printf("%d\n",a);
   }

这里o / p是c = -10,a = 40。因为最后一个陈述是b-a。该值分配给c。 (3)main()         {

    int a=10,b=30,c=0;
    if(c=({(a=a+b);0;}))
      {
       printf("%d\n",c);
       printf("%d\n",a);
      }
     printf("%d\n",c);
    }

这里o / p只是c = 0。如果没有执行,因为最后一个语句是0;

C遵循面向过程。()的关联性从左到右。