为什么收到链接错误,如果不使用内联

why receiving link error if not using inline?

本文关键字:如果不 链接 错误 为什么      更新时间:2023-10-16

以下classA.h

bool IsEqual(const float a, const float b)
{
    return std::fabs(a-b) < std::numeric_limits<float>::epsilon();
}

我收到链接错误

ld: 10 duplicate symbols for architecture i386
clang: error: linker command failed with exit code 1 (use -v to see invocation)

如果我加上inline,一切都很好。

我想知道为什么我必须添加inline

当这个函数定义在多个翻译单元中被发现时(这通常是头文件的情况,因为你通常在多个翻译单元中包含头文件,否则它们有什么意义?),你会从链接器中得到多个定义错误。

每个函数只允许一个定义。

但是标记函数inline是一种特殊情况,它允许您在多个翻译单元中使用此定义,只要定义相同即可。语言提供这一点,因为内联函数在定义立即可用时是最有效的(即在相同的翻译单元中,即可能在头文件中);在这个超级智能优化器的现代时代,inline并没有真正内在地导致实际的内联,但这并没有改变语言的事实。

如果在多个源文件中包含头文件,则相同的函数符号IsEqual将被定义多次。

传统上和在您的特殊情况下,当您使函数inline时是可以的,因为该函数实际上没有定义,并且函数体在每个调用站点上都被替换。

或者,您可以在classA.cpp中定义函数体,并声明classA.h

#ifndef __CLASS_HEADER_
#define __CLASS_HEADER_
bool IsEqual(const float a, const float b);
#endif
还有一种可能是将IsEqual声明为classA.h中某个类的静态成员。

因为IsEqual有多个定义,每次包含一个。