c++ - 拆分内联非成员运算符的声明和定义的正确方法(链接器问题)

标签 c++ visual-studio-2013 linker inline operator-keyword

我有一个包含 2 个项目的 visual studio 解决方案,其中一个是静态库。 在这个库中,我有以下带有一些重载运算符的类(成员和非成员):

namespace Vec
{
    class Vec2
    {
     ...
      inline Vec2& operator +=(const Vec2& b);

    };
    inline Vec2 operator+(const Vec2&a, const Vec2&b);
}

.cpp文件中的定义如下:

inline Vec2& Vec2::operator +=(const Vec2& b)
    {
        this->x += b.x;
        this->y += b.y;

        return *this;
    }
inline Vec2 Vec::operator+(const Vec2& a, const Vec2& b)
    {
        return Vec2(a.x + b.x, a.y + b.y);
    }

成员运算符的所有内容都可以正确编译和链接。非成员函数没有链接,错误如下:

Error 4 error LNK2019: unresolved external symbol "class Vec::Vec2 __cdecl Vec::operator+(class Vec::Vec2 const &,class Vec::Vec2 const &)" (??HVec@@YA?AVVec2@0@ABV10@0@Z) referenced in function _main

如果我将定义放在头文件中,或者将定义与声明分开但删除 inline 关键字,它会成功链接。

我做错了什么?

最佳答案

What am I doing wrong?

您的错误是从声明它的 header 中省略了 inline 函数的定义。如果您在不包含定义的 cpp 文件中使用该函数,您将违反语言规则。

§7.1.2/4(n3242 草案)

An inline function shall be defined in every translation unit in which it is odr-used...

如果您将函数声明为非内联,则上述规则不适用。如果您在 header 中包含定义,那么您就遵守了规则。

Proper way to split declaration and definition

您可以拆分它们,但不能拆分成单独的文件。

// in header

// declarations...
class Vec2
{
    Vec2& operator +=(const Vec2& b);
};
Vec2 operator+(const Vec2&a, const Vec2&b);

// definitions...
inline Vec2& Vec2::operator +=(const Vec2& b)
{
    ...
}
inline Vec2 operator+(const Vec2& a, const Vec2& b)
{
    ...
}

关于c++ - 拆分内联非成员运算符的声明和定义的正确方法(链接器问题),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30455820/

相关文章:

C++ 在 Windows 中发送一个简单的信号

c++ - C++ 中的模板

.net - 在同一次运行中同时运行 32 位和 64 位测试?

c# - Windows Phone 8.1 MediaCapture 卡住手机

c++ - C++ 命名空间中的内联函数

c++ - 如何强制 g++ 链接器加载不直接调用的符号 - 避免 undefined reference

c++ - 如何导入 2 个不同的时区以检查两者是否都是星期一?

c++ - 我们如何从 boost::asio::tcp::ip::read_some 调用中顺序接收多个数据?

visual-studio - 自动更改启动项目

objective-c - 如何忽略特定库的 -Objc 标志