gol*_*ean 45 c linker multiple-inclusions
我有一个头文件xh,它包含多个*.c源文件.此头文件定义了一些结构变量.
我在头文件的开头添加了多个包含防护措施:
#ifndef X_H
#define X_H
...
..
//header file declarations and definitons.
#endif//X_H
Run Code Online (Sandbox Code Playgroud)
在构建时,我得到与多个定义相关的链接器错误.我理解这个问题.
不会像我一样在头文件的顶部有多重包含防护,防止头文件xh的多个包含,从而避免xh中存在的变量的多个定义?
#pragma曾经不适用于这个特定的编译器,那么解决方案是什么?有人把这个答案发给了一个类似的问题.它似乎对我不起作用.这个解决方案如何运作?
Rod*_*ddy 57
如果链接器抱怨,则意味着您的标头中有定义而不仅仅是声明.这是一个错误的例子.
#ifndef X_H
#define X_H
int myFunc()
{
return 42; // Wrong! definition in header.
}
int myVar; // Wrong! definition in header.
#endif
Run Code Online (Sandbox Code Playgroud)
您应该将其拆分为源文件和头文件,如下所示:
标题:
#ifndef X_H
#define X_H
extern int myFunc();
extern int myVar;
#endif
Run Code Online (Sandbox Code Playgroud)
C来源:
int myFunc()
{
return 42;
}
int myVar;
Run Code Online (Sandbox Code Playgroud)
Pie*_*ter 14
使用include guard可防止一个编译单元包含两次头文件.例如,如果标题Bh包含Ah而B.cpp包含Ah和Bh,那么如果你没有使用包含保护,那么来自Ah的所有内容都将在编译B.cpp中声明两次.
你的包含警卫可以防止这种情况发生,一切都很好,直到现在.
但是你在链接时获得了多个定义,即两个编译单元定义相同的东西,这可能意味着你在头文件中有一个真正的定义,对所有变量使用extern,确保函数是内联的或在cpp文件中定义.
per*_*eal 12
标头保护仅适用于单个编译单元,即源文件.如果你碰巧有一个头文件多次,也许是因为所有的标题从包括main.c依次包括stdio.h然后守卫会有所帮助.
如果你有一个函数的定义f中x.h是由包括main.c和util.c,那么它就像复制和粘贴的定义f为main.c创建时main.o,做了同样的util.c创造util.o.然后链接器会抱怨,尽管你的标题守卫发生了这种情况.当然,由于这些警卫,可以有多个#include "x.h"陈述main.c.