#if定义的MACRO是否相当于#ifdef MACRO?
我有代码,我想有两种模式, debug和verbose 。 我在我的头文件中定义它们,
#define verbose TRUE #define debug TRUE
到目前为止,在我的代码中,我刚刚使用过
#if(debug) //code #endif
但使用起来更合适
#ifdef debug // code #endif
我读了一些关于预处理器宏的内容,但当时没有意义。 所以,我有疑问, #if defined MACRO
相当于#ifdef MACRO
? 哪个更好地启用/禁用特定代码段?
#ifdef MACRO #if defined (MACRO)
会做同样的事情。 但是,定义的(MACRO)只是一个在#if内部计算为0或1的表达式,它可以与其他表达式组合。 例如
#if defined (MACRO) && ! defined (MACRO2) // Do this #else // Do that #endif
尝试用#ifdef做到这一点 – 你不能,除非你的代码变得非常笨拙。
#if defined(MACRO)
与#ifdef MACRO
相同,但更长。 另一方面,它允许使用||
添加额外条件 或&&
。
#if MACRO
类似于#ifdef MACRO
但不是100%。 如果MACRO
为0
那么#if MACRO
将为负数 – 它需要定义MACRO
而不是0
。 #ifdef
仅检查它是否被定义,即使没有值( #define MACRO
)。
现在使用#if
和启用/禁用值为1或0的定义是现代的:
#define FLAG_X 1 // or 0
不,他们根本不相同。 如果MACRO
评估为非零,则编译#if MACRO
分支。 另一方面,如果定义了#ifdef MACRO
则编译#ifdef MACRO
分支,无论它评估的是什么。 所以
#include #define VAR_SET_TO_TRUE 1 #define VAR_SET_TO_FALSE 0 int main() { #if VAR_SET_TO_TRUE printf("#if VAR_SET_TO_TRUE\n"); #endif #if VAR_SET_TO_FALSE printf("#if VAR_SET_TO_FALSE\n"); #endif #if VAR_UNSET printf("#if VAR_UNSET\n"); #endif #ifdef VAR_SET_TO_TRUE printf("#ifdef VAR_SET_TO_TRUE\n"); #endif #ifdef VAR_SET_TO_FALSE printf("#ifdef VAR_SET_TO_FALSE\n"); #endif #ifdef VAR_UNSET printf("#ifdef VAR_UNSET\n"); #endif }
将输出
#if VAR_SET_TO_TRUE #ifdef VAR_SET_TO_TRUE #ifdef VAR_SET_TO_FALSE
注意行printf("#ifdef VAR_SET_TO_FALSE\n");
行printf("#if VAR_SET_TO_FALSE\n");
编译printf("#if VAR_SET_TO_FALSE\n");
不是。 第一个是编译的,因为定义了 VAR_SET_TO_FALSE
,即使它的值为false
。
如果我正确地阅读你的问题标题是误导性的,它应该是
Is #if MACRO equivalent to #ifdef MACRO?
它们不是等价的,但它们可以(通常是)用于指定打开或关闭的二进制模式。 在我看来,选择是个人偏好的问题。
您正在使用第一个选项,或者有
#define verbose true
要么
#define verbose false
然后使用其中一个检查模式
#if verbose
要么
#if !verbose
实际上,我建议您使用TRUE或1而不是true,使用FALSE或0而不是false,因为true和false,是(或可以是)C / C ++值,并且预处理器无法访问C / C ++值。
无论如何,指定二进制模式的另一种常用方法是定义标志或保持未定义,在这种情况下你可以使用
#define verbose any thing (including nothing) goes here
或者省略#define。
然后你可以测试是否定义了标志
#ifdef verbose
或其等价物
#if defined(verbose)
注意:在这种情况下,您不会测试标志的值,您只需要测试它是否已定义。
如果更方便的话,你也可以测试标志是否未定义
#ifndef verbose
或其等价物
#if !defined(verbose)
如果我们绞尽脑汁,我们就能想出差异。 但它是模糊的并且涉及未定义的行为,因此如果我们关心的是代码是否严格符合ISO C则无关紧要。
如果以前处理了#define defined ...
宏,则#if defined ...
表单容易出现不同的行为。 在ISO C99标准中,它是针对#if
和#elif
指令编写的:
在评估之前,将替换将成为控制常量表达式的预处理标记列表中的宏调用(除了由定义的一元运算符修改的宏名称之外),就像在普通文本中一样。
不要求defined
一元运算符被识别并保护不被视为宏; 它只是“预处理令牌中的一个将成为……表达”。 在此阶段识别defined
运算符仅用于保护其参数不受扩展的影响。
如果简单地允许define
为宏的defined
并且随后替换defined
出现(包括在#if
预处理指令的参数中),从而干扰#if defined
,同时不影响#ifdef
。
也许这个语言区域自C99以来就收紧了。