0

因此,在将一些代码添加到 JSON 的(反)序列化之后,我在基类和派生类之间进行转换时遇到了问题。我正在使用 nlohmann JSON 库。作为背景,这里是一般的原始设置(在 JSON 代码之前):

class Base;
class Derived : public Base;

std::unique_ptr<Derived> Foo(Node x) {
  std::unique_ptr<Derived> result;
  /* Set some fields */
  return result;
}


std::unique_ptr<Base> NodeToBase(Node x) {
  std::unique_ptr<Base> result = nullptr;

  switch (x->type):
    case (SomeType):
      result = Foo(x);

  return result;
}

在添加更改之前,以下断言有效:

static_assert(std::is_convertible<Derived*, Base*>::value);
static_assert(std::is_convertible<std::unique_ptr<Derived>, std::unique_ptr<Base>>::value);

接下来,我向我的基类和派生类添加了一些序列化函数,如下所示:

class Base {

  virtual nlohmann::json ToJson() const;
  virtual void FromJson(const nlohmann::json &j);

}

class Derived : public Base {

  nlohmann::json ToJson() const override;
  void FromJson(const nlohmann::json &j) override;
}

我还删除const了成员变量的所有量词,BaseDerived允许反序列化。

现在,编译后,static_assert上面的 's 不再起作用,并且出现以下错误。

foo.cpp:155:14: error: no viable overloaded '='
      result = Foo(x);
      ~~~~~~ ^ ~~~~~~~
/usr/local/Cellar/llvm@6/6.0.1/include/c++/v1/memory:2347:28: note: candidate function (the implicit copy assignment operator) not viable: no known conversion from 'unique_ptr<Derived, default_delete<Derived>>' to 'const unique_ptr<Base, default_delete<Base>>' for 1st argument
class _LIBCPP_TEMPLATE_VIS unique_ptr {
                           ^
/usr/local/Cellar/llvm@6/6.0.1/include/c++/v1/memory:2463:15: note: candidate function not viable: no known conversion from 'unique_ptr<Derived, default_delete<Derived>>' to 'unique_ptr<Base, default_delete<Base>>' for 1st argument
  unique_ptr& operator=(unique_ptr&& __u) _NOEXCEPT {
              ^
/usr/local/Cellar/llvm@6/6.0.1/include/c++/v1/memory:2555:15: note: candidate function not viable: no known conversion from 'std::unique_ptr<Derived>' to 'std::nullptr_t' (aka 'nullptr_t') for 1st argument
  unique_ptr& operator=(nullptr_t) _NOEXCEPT {
              ^
/usr/local/Cellar/llvm@6/6.0.1/include/c++/v1/memory:2474:15: note: candidate template ignored: requirement 'is_convertible<typename unique_ptr<Derived, default_delete<Derived> >::pointer, pointer>::value' was not satisfied [with _Up = Derived, _Ep = std::__1::default_delete<Derived>]
  unique_ptr& operator=(unique_ptr<_Up, _Ep>&& __u) _NOEXCEPT {
              ^

任何帮助,将不胜感激。我发现唯一可行的解​​决方法是替换:

result = Foo(x);

result = std::unique_ptr<Base>(reinterpret_cast<Base *>(Foo(x).release()));

4

0 回答 0