【问题标题】:How to properly name include guards in c++如何在 C++ 中正确命名包括警卫
【发布时间】:2018-04-06 08:27:40
【问题描述】:

我有 3 个头文件:

misc.h
MyForm.h
Registration.h

在 misc.h 文件中我放了

#ifndef MISC_H
#define MISC_H
#endif

在 MyForm.h 中,我放了

#include "misc.h"
#include "Registration.h"

在Registration.h中,我放了

#include "misc.h"

感谢您的帮助。

【问题讨论】:

  • “有重定向错误”你应该把它贴在这里然后相应地更改问题标题。
  • misc.h 底部有#endif 吗?
  • 这里的“重定向错误”有什么关系? minimal reproducible example 请。 /#pragma once?
  • #pragma once 是非标准的,只有部分编译器支持
  • 什么是“重定向错误”?是您自己翻译的,还是错误消息实际上使用了这些词?

标签: c++


【解决方案1】:

如何命名包括守卫在某种程度上是基于意见的,但可以提出一些建议:

1) 不要缩短它们,因为它们可能会与其他文件中定义的其他宏或您使用的实现或库发生冲突。

2) 使它们包含项目特定的前缀,以使它们唯一且明确。

3) 如果您的项目包含多个子部分“模块”/“库”等,请使保护名称包含模块的名称,以使其在您的项目中唯一 - 也包括文件名。

4) 确保不要使用保留名称,例如NULL、以数字开头的名称或以下划线后跟大写字母的名称以及包含连续下划线的名称;所有这些名称都保留给实现使用。

5) 对宏使用全部大写(只是一个常见的约定)。

对于名为“foo”的项目中名为“baz.h”的文件,在子模块“bar”中,我将守卫命名为FOO_BAR_BAZ_H

附言。确保所有您的标头使用包含防护(除了非常特殊和罕见的情况)。否则,您会遇到多个定义错误等问题。

【讨论】:

  • 请接受这个作为答案,谢谢!
【解决方案2】:

如何在 c++ 中正确命名包含守卫

通常的约定是只使用大写字符。数字和下划线也可以,除非不是作为第一个字符。包含保护必须是唯一的:该名称不得用于程序中的任何其他内容。

该名称不得保留,因此您不得使用NULL 等。此外,所有以下划线开头后跟一个大写字母的名称以及包含两个连续下划线的所有名称都是保留的。

MISC_H 不是保留的,但请记住,如果您在另一个路径中有另一个 misc.h,那么您不能使用相同的包含保护。通常最好使用较长的名称来唯一标识文件。也许使用某种前缀,例如公司名称或您自己的名字。通常_H 后缀用于与非保护宏分隔。

如果您在提出未保留的唯一名称时遇到问题,或者只是觉得这很乏味,那么您可以改用#pragma once。请注意,这不是标准的。我听说过关于不支持它的外来编译器的谣言,以及复杂的构建过程,其中硬链接文件没有得到应有的保护。如果您遇到此类问题,只需在之后添加标头保护即可。


您的其他标题似乎缺少包含警卫。如果您将它们包含在任何标题中,那么可能会有麻烦。保护所有头文件是一个好习惯。


我需要将#endif 放在 misc.h 的底部吗?

是的。守卫只保护define和endif之间的代码。

【讨论】:

  • “以下划线和大写字母开头的名称”-您的意思是“以下划线开头并后跟大写字母的名称”.. 作为一般经验法则,我通常建议 从不用前导下划线命名任何标识符,也不使用连续的下划线——这样你就不会遇到保留名称的麻烦。 :-)
  • @JesperJuhl 啊,这确实是危险的模棱两可。
【解决方案3】:

您应该在每个头文件中使用include guards,并且不应在包含防护之外。

包含守卫的名称可以是任何名称,只要它不太可能与任何其他名称发生冲突。您的 MyForm.h 的示例可能是:

#ifndef MYFORM_HEADER_
#define MYFORM_HEADER_

#include "misc.h"
#include "Registration.h"

/* all code here */

#endif

同样重要的是,在头文件的包含保护之外没有写入任何内容。

【讨论】:

    【解决方案4】:

    您需要将单个include guards 放在每个 标题中,特别是在MyForm.h

    #ifndef MYFORM_H
    #define MYFORM_H
    #include "misc.h"
    #include "Registration.h"
    // etc...
    #endif /*MYFORM_H*/
    

    Registration.h:

    #ifndef REGISTRATION_H
    #define REGISTRATION_H
    // actual code
    // etc...
    #endif /*REGISTRATION_H*/
    

    【讨论】:

      猜你喜欢
      • 2011-06-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-01-13
      • 1970-01-01
      • 2016-04-13
      相关资源
      最近更新 更多