33

我遇到了这段代码。我一般使用 '&&' 或 '||' 在for循环中分隔多个条件,但此代码使用逗号来执行此操作。

令人惊讶的是,如果我改变条件的顺序,输出会发生变化。

#include<stdio.h>

int main() {
    int i, j=2;

    for(i=0; j>=0,i<=5; i++)
    {
         printf("%d ", i+j);
         j--;
    }
    return 0;
}

输出 = 2 2 2 2 2 2

#include<stdio.h>

int main(){
    int i, j=2;

    for(i=0; i<=5,j>=0; i++)
    {
         printf("%d ", i+j);
         j--;
    }
    return 0;
}

输出 = 2 2 2

有人可以解释原因吗?它似乎只检查最后一个逗号分隔的条件。

4

7 回答 7

65

逗号运算符评估其所有操作数并产生最后一个的值。所以基本上无论你先写哪个条件,它都会被忽略,而第二个条件只会很重要。

for (i = 0; j >= 0, i <= 5; i++)

因此等价于

for (i = 0; i <= 5; i++)

这可能是也可能不是代码作者的意图,具体取决于他的意图 - 我希望这不是生产代码,因为如果编写此代码的程序员想要表达条件之间的 AND 关系,那么这是不正确的,并且&&应该使用运算符。

于 2013-05-31T13:59:14.157 回答
10

当然,你一开始说的就是对的,C逻辑运算符 &&||你通常用来“连接”条件(可以评估为真或假的表达式)的东西;正如其他用户所解释的那样,逗号运算符不是逻辑运算符,并且在该示例中使用它没有意义。您可以使用它来“连接” for 本身的语句:您可以使用 i 一起初始化和更新 j;或以其他 方式使用逗号运算符

#include <stdio.h>

int main(void)  // as std wants
{
  int i, j;

  // init both i and j; condition, we suppose && is the "original"
  // intention; update i and j
  for(i=0, j=2; j>=0 && i<=5; i++, j--)
  {
       printf("%d ", i+j);
  }
  return 0;        
}
于 2013-05-31T15:14:07.607 回答
5

逗号表达式采用最后一个(例如最右边)表达式的值。

所以在你的第一个循环中,唯一的控制表达式是i<=5; 并被j>=0忽略。

在第二个循环中,j>=0控制循环,并被i<=5忽略。


至于理由……没有理由。这段代码是错误的。逗号表达式的第一部分除了让程序员感到困惑之外什么都不做。如果一个认真的程序员写了这个,他们应该为自己感到羞耻并撤销他们的键盘。

于 2013-05-31T13:59:03.233 回答
3

不要使用此代码;写它的人显然对语言有根本的误解,并且不值得信赖。表达方式:

j >= 0, i <= 5

评估“j >= 0”,然后将其丢弃并且不做任何事情。然后它评估“i <= 5”并使用它,并且只有那个,作为结束循环的条件。当左操作数有副作用时,逗号运算符可以有意义地用于循环条件;你会经常看到类似的东西:

for (i = 0, j = 0; i < 10; ++i, ++j) . . .

其中逗号用于潜入额外的初始化和增量语句。但是显示的代码并没有这样做,或者其他任何有意义的事情。

于 2013-05-31T14:04:18.533 回答
3

维基百科告诉逗号运算符的作用:

“在 C 和 C++ 编程语言中,逗号运算符(由标记 表示,)是一个二元运算符,它计算其第一个操作数并丢弃结果,然后计算第二个操作数并返回此值(和类型)。”

于 2013-05-31T13:59:57.813 回答
2

C中有一个运算符称为逗号运算符。它按顺序执行每个表达式并返回最后一条语句的值。它也是一个序列点,这意味着每个表达式都保证在系列中的下一个表达式执行之前完全按顺序执行,类似于&&or ||

于 2013-05-31T13:59:24.417 回答
0

完成克罗克先生的回答,小心 ++ 或 -- 运算符,或者我不知道其他运算符。它们会影响循环。例如,我在一门课程中看到了与此类似的代码:

for(int i=0; i++*i<-1, i<3; printf(" %d", i));

结果将是 1 2 美元。所以第一条语句影响了循环,而下面的结果是很多零。

for(int i=0; i<3; printf(" %d", i));
于 2013-11-20T20:10:57.840 回答