“&”与“&&”实际上编译时标志有所不同?

时间:2016-09-02 04:51:20

标签: c++ c compilation

我习惯在编译时标志中使用以下语法:

> git checkout 444ea90502abc17eb2e55365e550a2e0dc95af61
error: inflate: data stream error (incorrect header check)
fatal: failed to read object 143fd2fe59980f9b4aec9b1b696e4d2ab5bd0465: Invalid argument
> git reset --hard
error: inflate: data stream error (incorrect header check)
fatal: failed to read object 143fd2fe59980f9b4aec9b1b696e4d2ab5bd0465: Invalid argument

通常建议我使用#if (defined(A) & defined(B)) 执行以下操作:

&&

我知道两个运算符之间的区别,而普通代码#if (defined(A) && defined(B)) 中的运算符会短路。但是,以上都是由编译器处理的。甚至重要的是我用的是什么?它是否会因某些无穷小的数量而影响编译时间,因为它不会评估第二个&&

3 个答案:

答案 0 :(得分:33)

由于defined(SOMETHING)会产生0或1,因此无论您使用&,都可以保证双方都是0或1,但不会产生技术差异或&&

这主要是关于良好的习惯(使用&可以延续到某些可能出错的情况)以及编写易于通过简单模式匹配来掌握的代码。其中&会导致毫秒暂停,而人们会考虑它是否可能是位级别的事情。

第三方面,你不能使用你可以在普通C ++代码中使用的关键字and

注意:
¹使用Visual C ++,您可以通过强制包含and来使用<iso646.h>。 功能

答案 1 :(得分:17)

根据C99标准,预处理器中使用的表达式是由C语言本身定义的常量表达式,并使用相同的引擎进行评估。因此,&&是基于其LHS短路的逻辑和运算符,&是按位运算符,没有预定义的评估顺序。

实际上,当您与defined()一起使用时,两者之间没有区别。但是,以下内容会有所不同:

#define A 2
#define B 5
#if (A && B)
printf("A && B\n");
#endif
#if (A & B)
printf("A & B"\n);
#endif

在这种情况下,A && B将被输出,但不会输出A & B(因为该按位的结果 - 并且是0

答案 2 :(得分:3)

我想补充一下以前的答案,在这种情况下它实际上很重要:

#define A 0
#define B 21
#if (A != 0) && (42 / A == B)
/* ... */
#endif

这里,如果A == 0,编译器不会中断。写(A != 0) & (42 / A == B)将使编译器抱怨除零。