首页 > 解决方案 > 接口的实现不是覆盖/实现虚拟方法

问题描述

所以我这里有这个界面......

template<typename T>
class SerdesTest {
public:
    virtual const char* type() = 0;
    virtual const char* serialize(const std::vector<T>&) = 0;
    virtual void deserialize(const char*) = 0;
    virtual bool test(const std::vector<T>&) = 0;
};

我想创建一个接口数组并添加像这样的不同实现......

std::vector<std::unique_ptr<SerdesTest<long>>> tests{};
tests.push_back(std::unique_ptr<SerdesTest<long>>(new JSONSerdes<long>()));

这是我的 impl 类的标题

...
#include "serdes_test.h"
...

template<typename Z>
class JSONSerdes: public SerdesTest<Z> {
public:
    const char* type() final;
    const char* serialize(const std::vector<Z>&) final;
    void deserialize(const char*) final;
    bool test(const std::vector<Z>&) final;

private:
    nlohmann::json _deserializedData;
};

然后这里是相关cpp文件的总结

#include "JSONSerdes.h"


template<typename T>
const char *JSONSerdes<T>::type() {
    ...
}

template<typename T>
const char *JSONSerdes<T>::serialize(const std::vector<T>& data) {
    ...
}

template<typename T>
void JSONSerdes<T>::deserialize(const char *serializedData) {
    ...
}

template<typename Z>
bool JSONSerdes<Z>::test(const std::vector<Z> &) {
    ...
}

然后是 cmake 可执行行...

add_executable(serdesPOC
        serdes/main.cpp
        serdes/serdes_test.h
        serdes/JSONSerdes.h
        serdes/JSONSerdes.cpp
        )

当我去构建时,我收到了这个错误

main.cpp.obj : error LNK2001: unresolved external symbol "public: virtual char const * __thiscall JSONSerdes<long>::type(void)" (?type@?$JSONSerdes@J@@UAEPBDXZ)
main.cpp.obj : error LNK2001: unresolved external symbol "public: virtual char const * __thiscall JSONSerdes<long>::serialize(class std::vector<long,class std::allocator<long> > const &)" (?serialize@?$JSONSerdes@J@@UAEPBDABV?$vector@JV?$allocator@J@std@@@std@@@Z)
main.cpp.obj : error LNK2001: unresolved external symbol "public: virtual void __thiscall JSONSerdes<long>::deserialize(char const *)" (?deserialize@?$JSONSerdes@J@@UAEXPBD@Z)
main.cpp.obj : error LNK2001: unresolved external symbol "public: virtual bool __thiscall JSONSerdes<long>::test(class std::vector<long,class std::allocator<long> > const &)" (?test@?$JSONSerdes@J@@UAE_NABV?$vector@JV?$allocator@J@std@@@std@@@Z)

我知道这是一个非常类似于虚函数的问题,它在基类中是 const 而在派生中不是 const但我不知道要更改什么,所以我可以将方法的实现保留在我的 cpp 文件中而不是头文件中.

感谢帮助!

标签: c++inheritancec++17

解决方案


@dewaffled 指出我的问题。这与我如何进行继承无关,而与我如何定义模板化方法有关。我通过将“JSONSerdes.cpp”重命名为“JSONSerdes.tpp”(只是为了语义一致)来修复它,然后将以下行添加到我的头文件的末尾

#include "JSONSerdes.tpp"

所以 impl 标头最终看起来像......

template<typename Z>
class JSONSerdes: public SerdesTest<Z> {
public:
    const char* type() final;
    const char* serialize(const std::vector<Z>&) final;
    void deserialize(const char*) final;
    bool test(const std::vector<Z>&) final;

private:
    nlohmann::json _deserializedData;
};

#include "JSONSerdes.tpp"

推荐阅读