【问题标题】:How to use #ifndef #define #endif properly in C++如何在 C++ 中正确使用#ifndef #define #endif
【发布时间】:2012-08-26 14:41:19
【问题描述】:

我正在做一个需要以下结构的项目:

这 2 个 CPP 文件包含类,这些类需要 H 文件 1 中的裸函数。类和裸函数需要 H 文件 2 中的变量。

我可以拆分 CPP 文件,以便它们使用 2 个单独的文件,其中包含 nakes 和他们需要的变量。但我更喜欢使用这种结构。

好像编译器跳过了#ifndef命令,我做了个测试:

主要:

#include <iostream>

//1>CPPFile2.obj : error LNK2005: "bool Test1" (?Test1@@3_NA) already defined in CPPFile1.obj
//1>CPPFile2.obj : error LNK2005: "bool Test2" (?Test2@@3_NA) already defined in CPPFile1.obj

int main()
{
}

CPP 文件 1:

#include <iostream>
using namespace std;

#include "HFile1.h"

CPP 文件 2:

#include <iostream>
using namespace std;

#include "HFile2.h"

H文件1:

#include "HFile2.h"

#pragma once
#ifndef Name1
#define Name1

//Use test1, this workes fine
//Use test2, this workes fine

#endif

H文件2:

#pragma once
#ifndef Name2
#define Name2

bool Test1 = false;
bool Test2 = false;

#endif

#ifndef #define #endif 结构怎么可能不能正常工作?

【问题讨论】:

  • 通常你不需要让那些包含守卫,因为你已经有一次#pragma。
  • 我在不支持#pragma once 的情况下添加了它们,但如果没有其中之一,它仍然无法工作。
  • 您违反了一个定义规则。您需要将Test1Test2 设为staticextern
  • 我确实可以看到其他一些问题。 HFile 1 如何使用 Test1 和 Test2?有功能吗?请记住,如果不包含 HFile2,您的 CPPFile1 将无法访问 Test1 和 Test2。除非您在 HFile1 中使用 extern 声明。

标签: c++ include compiler-errors


【解决方案1】:

您的问题是第二个标题是定义变量,而不仅仅是声明它们。程序中必须有一个定义,因此编译失败。这与包含守卫无关,因为包含守卫仅在单个翻译单元内进行保护。在您的情况下,每个 .cpp 文件都包含标头,因此分别定义相同的变量。

解决方案是仅在标题中声明变量并在单个翻译单元中定义它们:

#ifndef Name2
#define Name2
extern bool Test1;
extern bool Test2;
#endif
// single .cpp
bool Test1 = false;
bool Test2 = false;

虽然整个事情都有一些代码味道。您可能想要重新设计您的解决方案。在大多数情况下,使用全局变量并不是一个好的解决方案。

【讨论】:

    【解决方案2】:

    您收到 linking 错误;这与包括警卫无关。您已经在两个目标文件中定义了Test1Test2。相反,您需要确保只有一个目标文件定义它,而另一个 externs 它。

    【讨论】:

      【解决方案3】:

      永远不要在头文件中定义变量。你应该在 .cpp 中定义它,然后如果你想从另一个 .cpp 文件访问它,请创建一个带有“extern”的头文件。

      文件1.cpp

      bool Test1 = false; //define a var in your .cpp
      

      文件1.h

      extern bool Test1; //extern it in your header
      

      文件2.cpp

      #include "File1.h" //include the header of the variable
      
      void Somefunction()
      {
          if (Test1) //use the variable
          {
          //someting 
          }
      
      }
      

      但是,使用全局变量通常是一种不好的做法...

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2012-07-19
        • 2011-01-03
        • 2014-12-08
        • 1970-01-01
        • 2010-12-11
        • 2017-06-27
        • 2010-12-20
        相关资源
        最近更新 更多