例子:
#ifndef HEADER_h
#define HEADER_h
#endif
而不是HEADER_h
,我可以执行以下操作吗?
#ifndef HEADER
或者
#ifndef LIBRARY
或者
#ifndef SOMETHING
或者
#ifndef ANOTHERTHING
等等
标头保护只是一种约定,一种“技巧”,利用预处理器条件。在使用标头保护时,您正在创建一个带有名称的宏,并检查该宏是否已经定义。
这个宏并没有什么神奇之处,它可以将它绑定到标题的文件名,因此您可以随意调用它(在合理范围内)。
但是,这并不意味着您应该编写#ifndef URGLEBURGLE
. 您希望名称有用且独特,否则没有多大意义。
通常,类似的东西#ifndef [PROJECTNAME]_[FILENAME]_INCLUDED
是个好主意。
是的,您可以随意命名包含保护符号,但请记住,它们在标头中应该是唯一的。你绝对不想要标题
// first.h
#ifndef NON_UNIQUE_H
#define NON_UNIQUE_H
void foo();
#endif
还有一个
// second.h
#ifndef NON_UNIQUE_H
#define NON_UNIQUE_H
void bar();
#endif
当您将两者都包含在一个翻译单元中时,一个将“获胜”并且其声明将可见,例如
// main.cpp
#include "first.h" // now, NON_UNIQUE_H is defined
#include "second.h" // NON_UNIQUE_H already there, doesn't do anything
int main(int, char**)
{
bar(); // error, won't compile, bar() isn't declared
}
除了规避这种情况的必要性之外,最好在整个项目中坚持一些约定。一种经典的方法是将头文件基本名称转换为大写并附加_H
. 如果您在不同目录中有具有相同基本名称的头文件,则可以包含目录名称,例如SUBDIR_FOO_H
和OTHERSUBDIR_FOO_H
. 但这取决于你。
您可以使用类似的结构
#if !defined(HEADER) || !defined(LIBRARY)
在您的问题中,您正在使用
#ifndef HEADER_h
#define HEADER_h
#endif
它与“#pragma once”相同,是的,您可以使用不同的定义名称。在您的情况下,LIBRARY,SOMETHING,HEADER_h - 定义,您可以在代码中设置(#define MY_VAR_NAME)或通过编译器选项(标志 -DMY_VAR_NAME)。
您的示例是所谓的标头保护,它允许我们确保标头的内容只包含一次。但是,这不是#ifndef
.You 的唯一用途。您可以将#ifndef
其用于条件编译,如
#ifndef NO_DEBUG
do_some_debug_stuff();
#endif
因此,它不仅适用于标题保护,而且通常您必须仔细选择要引入的符号的名称,以防止它们与其他地方定义的符号发生冲突。只是标题保护如此普遍以至于存在某些约定(例如,使用FOLDER_FILENAME_H
通常足以确保唯一性)。您需要注意某些名称是保留的(例如以两个下划线或下划线后跟大写字母开头)。