0

我试图将一些多态类拆分为一个 dll 文件。然后我得到一个未注册的多态类型的异常。问题似乎是代码创建了两个用于查找多态对象的映射实例(由模板类 grain::detail::StaticObject 保留)。如果我将 CEREAL_REGISTER_TYPE 放入进行序列化的项目中,那么一切正常。
所以我想知道是否有人知道是否可以做一些技巧来在 dll 文件中进行注册?
是否可以强制程序使用谷物::detail::StaticObject 类的相同实例?

4

2 回答 2

0

谷物 v1.1.0开始,可以通过将多态类型注册移动到头文件来解决此问题,这将确保包括该头文件的任何翻译单元正确初始化其静态对象。请记住在调用注册宏之前包含您希望绑定到的档案。

[主要谷物文档] 站点 ( http://uscilab.github.io/cereal/polymorphism.html )上提供了更多信息,该站点也已针对 1.1 进行了更新。

于 2015-01-19T21:38:46.463 回答
0

通过在我的 DLL 依赖链底部的 DLL 中的 hpp 中添加以下语句,我设法用 1.3.0(也应该与 1.1 一起使用)解决了这个问题。我们称之为core.dll。在该 DLL 中,我将有一个名为 config.hpp 的文件,其中包含以下传统宏。CMake 将在为 core.dll 生成构建脚本时定义 core_EXPORTS

#if defined(_MSC_VER) || defined(__MINGW32__) || defined(__MINGW64__)
#  if defined(core_EXPORTS)
#    define CORE_DECL __declspec(dllexport)
#  else
#    define CORE_DECL __declspec(dllimport)
#  endif
#endif

然后在 core.dll 的另一个 export.hpp 我有以下

namespace cereal {
    namespace detail {
        // these declspecs will ensure that the polymorphic loader/saver registrations will
        // all happen against the binding maps in core.dll
        template class CORE_DECL StaticObject<InputBindingMap<PortableBinaryInputArchive>>;
        template class CORE_DECL StaticObject<InputBindingMap<JSONInputArchive>>;
        template class CORE_DECL StaticObject<OutputBindingMap<PortableBinaryOutputArchive>>;
        template class CORE_DECL StaticObject<OutputBindingMap<JSONOutputArchive>>;
        // add similar statements for other archive types as needed
        template class CORE_DECL StaticObject<Versions>;
    } // namespace detail
} // namespace cereal

其他 dll 项目中的所有其他 cpp 文件将 #include core/export.hpp 从而告诉链接器使用 core.dll 中的谷物静态对象。如果您调试 InputBindingCreator 构造函数,您会注意到现在每个类都在同一个绑定映射中注册。

我认为将以上内容添加到有关此主题的谷物文档中会很有用。

于 2019-12-19T16:05:12.953 回答