j_r*_*ker 32

assert(foo == bar);NDEBUG定义时,还有什么可以编译为空?

  • 好吧,现在我发现它让它编译成类似于'0`或`((void)0)的东西也可能会很好,但无论如何...... (3认同)
  • `do {} while(0)` (2认同)

mou*_*iel 13

这是C和C++表达NOP的方式.

  • @ jpinto3912:事实上```几乎肯定会编译为*根本没有指令*,而不是目标平台的'NOP`指令. (23认同)
  • 我对此表示怀疑。更有可能是内在的或汇编。没有说明!= NOP。 (3认同)

小智 10

显然我们可以这么说

for(;;) {
  // stuff
}
Run Code Online (Sandbox Code Playgroud)

谁能活下去呢?

  • 这不是一个好例子,因为,例如,第二个分号不用于结束语句.for的第二个条款是表达式; 并将其留空是一种特殊情况,使其等同于真实. (8认同)
  • 这实际上是一个糟糕且不相关的例子.`for`标题内的`;`与OP问题中的`;`没有任何共同之处.你在`for`标题里面的内容根本就不是陈述.上面`for`中的`;`不是"空语句".`for`中的`;`只是`for`语法的硬编码字符,没有特殊含义.只有`for`标题的第一部分在语言规范中被称为"语句",但即使是那个也是一种特殊的`for`特定的伪语句,它有自己的专用语法. (2认同)
  • ......换句话说,`for(;;)`合法的事实与空陈述是合法的事实完全无关.这两者是由他们自己的,完全不相关的语法和语言规范部分描述的. (2认同)

Dan*_*ego 8

我不是语言设计师,但我给出的答案是"为什么不呢?" 从语言设计的角度来看,人们希望规则(即语法)尽可能简单.

更不用说"空表达"有用,即

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

将死等待(不是很好用,但仍然使用).

编辑:正如在对这个答案的评论中所指出的,任何有价值的编译器可能都不会忙于等待这个循环,并将其优化掉.但是,如果在head头本身(除了i ++之外)有一些更有用的东西,我已经看到(奇怪地)使用数据结构遍历,那么我想你仍然可以构造一个空体循环(通过使用/滥用"for"构造).

  • 那真的会等吗?编译器能否优化掉循环,因为没有任何反应? (3认同)

Tom*_*Tom 7

老实说,我不知道这是否是真正的原因,但我认为更有意义的是从编译器实现者的角度考虑它.

大部分编译器是由分析特殊语法类的自动化工具构建的.有用的语法似乎很自然地允许空语句.当它不改变代码的语义时,检测这样的"错误"似乎是不必要的工作.空语句不会执行任何操作,因为编译器不会为这些语句生成代码.

在我看来,这只是"不要修复没有破坏的东西"的结果......


Tho*_*thy 5

你希望能够做到这样的事情

while ( fnorble(the_smurf) == FAILED )
    ;
Run Code Online (Sandbox Code Playgroud)

并不是

while ( fnorble(the_smurf) == FAILED )
    do_nothing_just_because_you_have_to_write_something_here();
Run Code Online (Sandbox Code Playgroud)

但!请不要在同一行写下空语句,如下所示:

while ( fnorble(the_smurf) == FAILED );
Run Code Online (Sandbox Code Playgroud)

这是混淆读者的一种非常好的方法,因为很容易错过分号,因此认为下一行是循环的主体.请记住:编程实际上是关于通信 - 不是与编译器有关,而是与其他人一起阅读您的代码.(或者三年后你自己!)


小智 5

好的,我会将此添加到您可能实际使用的最坏情况:

for (int yy = 0; yy < nHeight; ++yy)
{
    for (int xx = 0; xx < nWidth; ++xx)
    {
        for (int vv = yy - 3; vv <= yy + 3; ++vv)
        {
            for (int uu = xx - 3; uu <= xx + 3; ++uu)
            {
                if (test(uu, vv))
                {
                    goto Next;
                }
            }
        }

    Next:;
    }
}   
Run Code Online (Sandbox Code Playgroud)

  • +1 有用的例子:因为 goto 标签后面必须有一个语句,但在极少数情况下你需要一个 goto 标签通常只需要在循环的底部,所以你需要一个 NOP 语句。您可能会反对 goto,但有时最好(并且更具可读性)使用 goto 退出深度嵌套的循环,而不是使用额外的变量和 if() 语句单独退出每个循环。 (2认同)