标签: multiple-inclusions

为什么我的编译保护不能防止多个定义包含?

我有一个头文件xh,它包含多个*.c源文件.此头文件定义了一些结构变量.

我在头文件的开头添加了多个包含防护措施:

#ifndef X_H
#define X_H
...
..
//header file declarations and definitons.


#endif//X_H
Run Code Online (Sandbox Code Playgroud)

在构建时,我得到与多个定义相关的链接器错误.我理解这个问题.

  1. 不会像我一样在头文件的顶部有多重包含防护,防止头文件xh的多个包含,从而避免xh中存在的变量的多个定义?

  2. #pragma曾经不适用于这个特定的编译器,那么解决方案是什么?有人把这个答案发给了一个类似的问题.它似乎对我不起作用.这个解决方案如何运作?

c linker multiple-inclusions

45
推荐指数
5
解决办法
4万
查看次数

重复多重定义错误,在多个cpps中包含相同的标头

因此,无论我做什么,我似乎都无法避免由于我在同一项目中的多个源代码文件中包含相同的头文件而使Dev C++发出大量多重定义错误.我非常希望避免将我的所有源代码转储到一个文件中,并且只包含一次标题,因为这将使我的文件很长并且难以管理.

从本质上讲,这是正在发生的事情:

#ifndef _myheader_h
#define _myheader_h

typedef struct MYSTRUCT{
int blah;
int blah2; } MYSTRUCT;

MYSTRUCT Job_Grunt;
MYSTRUCT *Grunt = &Job_Grunt;
MYSTRUCT Job_Uruk;
MYSTRUCT *Uruk = &Job_Grunt;

int Other_data[100];

void load_jobs();

#endif
Run Code Online (Sandbox Code Playgroud)

示例Cpp文件(它们几乎都看起来像这样):

#include "myheader.h"

void load_jobs(){

Grunt->blah = 1;
Grunt->blah2 = 14;

Uruk->blah = 2;
Uruk->blah2 = 15;

return; }
Run Code Online (Sandbox Code Playgroud)

请记住,我有大约5个包含这个标题的cpp文件,每个文件都处理头文件中找到的不同类型的结构.在这个例子中,当实际头文件中有大约4-6个不同的结构,并且有更多的成员时,只有一个结构包含几个成员.我在其中包含的所有文件都遵循您在此示例中看到的相同公式.

现在我明白了标头防护只能阻止每个单独的cpp文件多次包含头文件.似乎正在发生的事情是,当编译器在每个cpp的开头读取include时,它会再次定义头文件,这会导致它吐出以下行和行:

Multiple Definition of Uruk, first defined here  
Multiple Definition of Job_Uruk, first defined here  
Multiple Definition of Grunt, first defined here  
Multiple Definition of Job_Grunt, first …
Run Code Online (Sandbox Code Playgroud)

c++ multiple-inclusions multiple-definition-error dev-c++

15
推荐指数
4
解决办法
4万
查看次数

什么类型的头文件不应该被保护以防止多个包含?

我读了dcmtk源代码,并在ofstdinc.h中找到了注释:

// this file is not and should not be protected against multiple inclusion
Run Code Online (Sandbox Code Playgroud)

什么样的头文件不应该被保护免受多重包含?

c c++ multiple-inclusions

15
推荐指数
2
解决办法
572
查看次数

使用带有#ifdef标头防护的.c文件链接.h文件

我无法链接.h和.c文件,我也阅读了一些关于这个问题的线程,所有这些都有点模糊,但我仍然无法完全掌握它的概念,并且我有很多链接问题,说我有bc和bh,我将在ac中使用,我很困惑是否包括bh ac和bc cuz bc本身需要知道bh中定义的结构,我有一些功能,其原型在bh中定义在bc中也使用了bh中的结构,我不知道在bc cuz中的bh,因为我知道bh更像是将使用bc中的函数的ac接口.这里有一个更清晰的例子

bh文件

typedef struct{
int x, y;
}myStruct;

void funct1(myStruct);
void funct2(myStruct);
Run Code Online (Sandbox Code Playgroud)

bc文​​件

void funct1(myStruct x)
{
    //do something
}

void funct2(myStruct y)
{
     //do something
} 
Run Code Online (Sandbox Code Playgroud)

ac文件

#include "b.h"

int main()
{
myStruct x;
  funct1(x);
  funct2(y);
return 0;
}
Run Code Online (Sandbox Code Playgroud)

执行cygwin中的命令:gcc bc ac -g

现在令人困惑的部分,我有一个链接错误,其中当bc编译时,它无法检测结构和原型在bh Cuz我所知道的是bh用于链接bc从ac但是当两个.c编译时似乎那个bc找不到它的结构和原型,

为什么我没有在bc中包含bh? 答案:因为我知道,因为bh已经包含在交流中了,当我再次将其包含在bc中时,我会做双重包含< - 这就是我到目前为止学到的东西,我知道有#ifdef但似乎它不会起作用,也许我还是不知道如何使用它,如果你知道的话请随意讨论这个.

如果你有任何关于如何去做的想法,请随时告诉我一些.

有一个#ifdef指令,但我似乎无法知道如何做到这一点.

注意:如果有任何拼写错误的单词,请假设所有上面的代码都是完全正确的,请忽略,我只是在.h和.c之后的内容之后

c multiple-inclusions

12
推荐指数
1
解决办法
5万
查看次数

避免双重包含:预处理器指令与makefile

我正在努力从frankenstein和一个成千上万行的程序转移到结构良好,有组织的多文件程序.现在似乎很自然(天真)的是为我的三个文件做一个标题包含的三角形:
file_1包含file_2,file_4
file_2包含file_3,file_4
file_3包含file_1 ....等等
这些文件有变量,我需要在其他文件之间的方法,结构等.

当然,我有双重包含错误.

我的问题:我应该通过在头文件中使用预处理程序指令来避免这些问题(例如,在头文件中完全包含结构,方法等),或者我应该使用makefile编译(我听说也可以用来解决这个问题 - - 但我从未做过一个)?

c++ makefile multiple-inclusions c-preprocessor

5
推荐指数
2
解决办法
6221
查看次数

Clang++ 已更新,无法找到某些标头,尽管它们位于包含目录中

所以我在 mac 上想要尝试最新的 llvm 版本,而不必等待它们在 xcode 命令行工具上传递。

因此,我从他们的下载页面下载了 LLVM 10 版本的预构建二进制文件,并将其放在名为 llvm 的文件夹中。因此,可以在 ~/SDKs/LLVM/bin 中找到 clang 可执行文件。

我制作这个程序:

#include <string>
#include <iostream>

int main(int argc, char const *argv[])
{
    std::string myString("Hello World");
    std::cout << myString;
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

并运行:

~/SDKs/Clang+LLVM10/bin/clang++ main.cpp
Run Code Online (Sandbox Code Playgroud)

我收到这个致命错误:

~/SDKs/Clang+LLVM10/bin/../include/c++/v1/string.h:60:15: fatal error: 
      'string.h' file not found
#include_next <string.h>
              ^~~~~~~~~~
Run Code Online (Sandbox Code Playgroud)

这没有意义,因为我可以使用 finder 手动找到 string.h,并且它就在错误中引用的文件夹中。

我猜这与 clang++ 首先搜索我的系统包含路径有关,在那里找到旧的 string.h ,因此选择不使用更新的 string.h ,从而导致错误?


一些附加信息(如果有帮助的话):

运行这个(新编译器)

~/Programming/SDKs/Clang+LLVM10/bin/clang++ -Wp,-v -E -xc -x c++ /dev/null
Run Code Online (Sandbox Code Playgroud)

给我:

clang -cc1 version 10.0.0 based upon LLVM …
Run Code Online (Sandbox Code Playgroud)

c++ std multiple-inclusions include-path clang++

3
推荐指数
1
解决办法
5610
查看次数