#if 0 … #endif块究竟做了什么?
在C / C ++中
在#if 0
/ #endif
块之间放置的代码会发生什么变化?
#if 0 //Code goes here #endif
代码是否被跳过,因此不会被执行?
它不但不会被执行,甚至不会被编译。
#if
是一个预处理器命令,在实际的编译步骤之前被执行。 该块内的代码不会出现在已编译的二进制文件中。
它通常用于暂时删除代码段,以便稍后将其重新打开。
除了一个重要的区别之外,它与注释块相同:嵌套不是问题。 考虑这个代码:
foo(); bar(x, y); /* x must not be NULL */ baz();
如果我想评论一下,我可以试试:
/* foo(); bar(x, y); /* x must not be NULL */ baz(); */
Bzzt。 语法错误! 为什么? 因为块注释不能嵌套,所以(如你可以从SO的语法高亮中看到的那样) */
在单词“NULL”之后终止注释,使得baz
调用没有被注释掉,而*/
baz
之后是一个语法错误。 另一方面:
#if 0 foo(); bar(x, y); /* x must not be NULL */ baz(); #endif
作品评论整个事情。 #if 0
将互相嵌套,如下所示:
#if 0 pre_foo(); #if 0 foo(); bar(x, y); /* x must not be NULL */ baz(); #endif quux(); #endif
虽然当然这可能会有点混乱,如果没有正确评价,会成为维修头痛。
它会永久地注释该代码,以便编译器永远不会编译它。
编码器可以稍后更改#ifdef,以便在程序中编译该代码(如果他愿意的话)。
这就像代码不存在一样。
#if 0 … #endif块究竟做了什么?
它告诉你,作者显然从未听说过版本控制系统。 而这又反过来告诉你尽可能远地跑…
我想添加#else
情况下:
#if 0 /* Code here will NOT be complied. */ #else /* Code will be compiled. */ #endif #if 1 /* Code will be complied. */ #else /* Code will NOT be compiled. */ #endif
当预处理器看到#if时,它检查下一个标记是否具有非零值。 如果是这样,它会保留编译器的代码。 如果没有的话,它会去掉那些代码,这样编译器就不会看到它。
如果有人说#if 0,他们正在有效地注释掉代码,所以它永远不会被编译。 你可以这样想,就好像他们把/ * … * /放在了一起。 这不完全相同,但它有相同的效果。
如果你想了解详细发生的事情,你可以经常看看。 许多编译器将允许您在预处理器运行后看到文件。 例如,在Visual C ++中,开关/ P命令将执行预处理器,并将结果放在一个.i文件中。
以#
开始的行是预处理器指令 。 #if 0 [...] #endif
块不会编译到编译器,也不会生成机器码。
您可以使用源文件ifdef.cxx
来演示预处理器会发生什么情况:
#if 0 This code will not be compiled #else int i = 0; #endif
运行gcc -E ifdef.cxx
会显示你编译的内容。
您可以select使用此机制来防止在开发周期中编译的代码块,但是您可能不希望将其检入到源代码pipe理中,因为它只会增加代码的可读性并降低可读性。 如果这是一段已被注释掉的历史代码,那么应该删除它:源代码pipe理包含历史logging,对不对?
另外, C和C ++的答案可能是一样的,但是没有一种叫做C / C ++的语言,引用这种语言不是一个好习惯。
不完全的
int main(void) { #if 0 the apostrophe ' causes a warning #endif return 0; }
它显示“TC:4:19:警告:缺less终止”字符“与海湾合作委员会4.2.4
这是一个便宜的方式来评论,但我怀疑它可能有debugging潜力。 例如,假设您有一个将值输出到文件的构build。 你可能不希望在最终版本中,所以你可以使用#if 0 … #endif。
另外,我怀疑为了debugging目的,更好的方法是做:
#ifdef DEBUG // output to file #endif
你可以做这样的事情,这可能更有意义,你所要做的就是定义DEBUG来查看结果。