我有一个包含简单结构的标头util.hpp
:
// util.hpp
struct Point {
float x;
float y;
};
两个cpp文件,我们称它们为a.cpp
和b.cpp
,它们都包含util.hpp
:
// a.cpp
#include "util.hpp"
void funcA(float _x, float _y) {
Point p;
p.x = _x;
p.y = _y;
// ...
}
// b.cpp
#include "util.hpp"
void funcB(float _x, float _y) {
Point p;
p.x = _x;
p.y = _y;
// ...
}
int main() {
// ...
}
当我分别编译a.cpp
和b.cpp
并将它们链接在一起时,没有错误。
那是为什么?由于我在两个文件中都包含util.hpp
,所以我们不会有struct Point
的双重定义吗?
例如,当我像这样向util.hpp
添加变量定义时:
// util.hpp
struct Point {
float x;
float y;
};
// New variable
int foo;
链接时出现以下错误:
g++ a.o b.o -o test -O0
b.o:(.bss+0x0): multiple definition of `foo'
a.o:(.bss+0x0): first defined here
这对我来说很有意义,但为什么结构不会出现相同的错误?
答案 0 :(得分:4)
b.o :(。bss + 0x0):'foo'的多个定义
拥有
// util.hpp ... // New variable int foo;
每次您包含 util.hpp 时,您再次定义全局变量foo,从而产生错误
只需在头文件中声明(extern int foo;
)并将其定义在一个源文件中
结构点没有相同的问题,因为这是类型定义,而不是全局变量定义
答案 1 :(得分:3)
类型定义(struct
,union
,class
,enum
)只是编译器如何在内存中布置某些内容的“蓝图”但不要自行生成代码或符号。
在C ++中,您还可以具有成员函数和运算符以及静态成员变量,但是从技术上讲,它们不是struct / class的组成部分,而是带有< / em> struct / class,因此您只能全局定义一次。
就像foo
的全局变量定义一样,如果在包含多次的文件中完成,则此定义将无效。但是您可以安全地多次声明。