在我阅读this question的接受答案时,我有以下问题:
通常,方法在头文件(.hpp
或其他)中定义,并在源文件(.cpp
或其他)中实现。
包含“源文件”(#include <source_file.cpp>
)的不良做法的一个主要原因是它的方法实现会被复制,从而导致链接错误。
当一个人写道:
#ifndef BRITNEYSPEARS_HPP
#define BRITNEYSPEARS_HPP
class BritneySpears
{
public:
BritneySpears() {}; // Here the constructor has implementation.
};
#endif /* BRITNEYSPEARS_HPP */
他正在给出构造函数的实现(这里是一个“空”实现,但仍然如此)。
但为什么然后多次包含此头文件(又名在不同的源文件上)不会在链接时生成“重复定义”错误?
答案 0 :(得分:13)
内联函数是“一个定义规则”的例外:允许您在多个编译单元中具有相同的实现。如果函数声明为inline
或在类定义中实现,则函数是内联的。
答案 1 :(得分:7)
在类定义中具有实现的成员函数被视为内联函数。内联函数不受一个定义规则的约束。
特别是当链接器看到具有相同签名的两个内联函数时,它将它们视为相同的函数,并且只选择其中一个。这可以导致to really weird hard to detect problems。
答案 2 :(得分:2)
因为它是“内联”功能。内联函数可以根据您的喜好多次包含在标题中,并且不会导致重复的定义链接器错误。
编译器也会尝试将它们内联,因此,在上面的示例中,编译器将尝试并完全取消对构造函数的调用。