#ifndef NULL
#define NULL NULL
#endif
这段代码在gcc中编译时没有警告/错误。请问有人能解释一下这里的预处理器是做什么的吗?
#ifndef NULL
#define NULL NULL
#endif
无论在哪里编译器看到文本“NULL”,它都会用文本“NULL”替换它。这就像在代码中执行搜索和替换“NULL”为“NULL”。这不是非法的,只是有点奇怪 :)
#ifndef NULL
#define NULL (void *)0
#endif
这样就可以防止NULL被定义成那样了。
const int NULL = 0;
。 - Greg Bacon这是正常现象:
#ifndef JON_SKEET
#define JON_SKEET JON_SKEET
#endif
我曾经看到过这样的代码,它将一个值从编译器命名空间(一般来说,并不是C++中的namespace
)带到了预处理器命名空间中,例如:
// In the compiler namespace, not in the preprocessor namespace
static int const FOO = 1234;
// Bring the constant into the preprocessor namespace as well
#ifndef FOO // <---- FOO really is undefined here.
#define FOO FOO
#endif
真的很丑陋。
个人而言,我还没有找到这种东西的用途,但它仍然存在。
编辑:虽然我见过这个,但我不知道为什么它会有用,除了检查代码中是否定义了"FOO
"作为预处理器符号;也许在处理一些遗留代码时。 任何人都可以解释吗?
static int const FOO = 1234;
这一行中它将被替换。我不知道为什么你会愿意在这些情况下继续进行。#define FOO FOO
可能有意义,正如你所说的,如果你要用常量替换宏,但又不想更改一些检查其是否被定义的旧代码。但是在定义常量 FOO 时让 FOO 被定义为其他东西,对我来说听起来像是麻烦事。 - Steve Jessop显然,这不是作为宏使用,而是作为编译标志使用。您是否在代码的其他地方看到过 #ifdef NULL
或 #ifndef NULL
?
将“NULL”作为这样的标志使用非常奇怪,但我见过更奇怪的用法 (#define TRUE FALSE
)...
回答关于预处理器的问题:
除非有先前的代码取消了 NULL 的定义,否则它会完全跳过 #define NULL NULL
。NULL 几乎肯定已经被定义了。在 C++ 中,由于 C++ 更严格的类型检查,使用 0 是首选。如果必须使用 NULL,则最好声明 const int NULL = 0;
(请参见 Stroustrup 的第 5.1.1 节)。
这不是简单地将NULL定义为字符序列"NULL"吗?
#define NULL "NULL"
。 - Andreas Bonini"NULL"
。 - catchmeifyoutry