我正在尝试检查是否已使用C ++宏声明了#include <file.h>
。
在file.h中我做:
#ifndef FILE.H
#define FILE.H
class A
{
//do routines
};
#endif
在名为second.h
的第二个文件中,我想检查是否已包含file.h
。
典型的伪代码:
#ifndef "file.h"
#include "file.h"
#endif
#ifndef SECOND.H
#define SECOND.H
class second
{
//do routine
};
#endif
我尝试了一些#ifndef
指令,但没有快乐。有谁知道如何实现这个目标?
答案 0 :(得分:10)
其他人都已正确包含了包含保护宏。
#ifndef FILE_H
#define FILE_H
// Code here
#endif
但其他人错过了关于正确用法的问题的第二部分:
这是一个不良用法的例子:
#ifndef FILE_H
#include "file.h"
#endif
#ifndef SECOND_H
#define SECOND_H
class second
{
//do routine
};
#endif
这是不正确的(虽然正确可能太强了)。
每个文件中的包含警卫应该包含其整个内容。因此,在第二个文件中,#include "file.h"
应该在包含警戒中。
此外不需要测试将在文件内部完成的包含。因此该文件应如下所示:
#ifndef SECOND_H
#define SECOND_H
#include "file.h"
class second
{
//do routine
};
#endif
你的大卫卫兵太小了。其他人很可能会使用这些;这将导致各种奇怪的碰撞。
使警卫独特的一个好方法是使用前缀,您的全名(或昵称),或者如果您拥有自己的注册网站,则使用其域名。然后我还添加了包含该文件的目录层次结构的一部分。
#ifndef WEBSITE1_NAMESPACE1_NAMESPACE2_FILENAME_H
#define WEBSITE1_NAMESPACE1_NAMESPACE2_FILENAME_H
#endif
另一种替代方法(特别是如果您在Windows上工作)是生成GUID。只需为每个文件生成一个新文件。
最后一点:如果内容是绝对必要的,则只包含头文件中的其他文件。如果此文件具有类second定义的类型定义,则只需要包含“file.h”。如果您的类仅将该类用作指针或引用,则更喜欢使用前向声明而不是头文件。
您必须#include
的场景:
objects
objects
作为参数objects
的方法请注意,我使用术语“对象”。如果它们是引用或指针,那么这不算数。在这些情况下,您可以使用前向声明来解决问题。
答案 1 :(得分:7)
:
#ifndef FILE_H
#define FILE_H
...
...
...
#endif
然后检查file.h是否包含在:
中#ifdef FILE_H
答案 2 :(得分:2)
在file.h中
#ifndef FILE_H_
#define FILE_H_
#else
#error file.h has been included previously
#endif
但如果多次包含file.h
,这将导致程序无法编译。您可能想要的是
#ifndef FILE_H_
#define FILE_H_
// contents of file.h go here
#endif
这将防止因多次包含而导致的编译错误/警告。
答案 3 :(得分:2)
简单的原因
#ifndef FILE_H
标题中的行是这样的,在第二个和更多内容中,文件是无操作。那些#行合在一起被称为“包含守卫”。
因此,只需做#include "file.h"
将会在第二个文件中执行您要执行的操作。
(预处理器可能会在丢弃其内容之前打开并读取该文件,但是假设它在缓存中是合理的,因此在一般情况下没有预期的编译器性能增益。
如果你抱怨没有包含文件,你可以自己加入。也许你想禁止在包含另一个文件时包含文件,所以它们是 - 或者;或严格的包含顺序(可能是设计问题的症状)。或者在(未)包含某些内容时使用替代代码。
在这种情况下,#ifdef X
或#ifndef X
,其中X与包含守卫中使用的匹配,将起作用。
答案 4 :(得分:1)
这样做的典型方式是:
#ifndef _FILE_H_
#define _FILE_H_
// some code
#endif
这样可以防止多次包含相同的标题。