启用非公共继承的技巧

这是与我的previous question相关的后续调查,在该调查中我调查了这个问题,发现在公共继承关系上,上下转换似乎正常工作。例如,此代码甚至无法编译:

class A {
};

class B : protected A {
};

int main() {
  B b;
  static_cast<A*>(&b);
};

G ++出现以下错误:

t.cc: In function ‘int main()’:
t.cc:10:21: error: ‘A’ is an inaccessible base of ‘B’
   10 |   static_cast<A*>(&b);
      |                     ^

但是,我认为我发现了以下技巧来克服此限制。 我们可以在类内部进行强制转换,然后将强制转换功能导出为公共方法:

#include <iostream>

class A {
};

class B : protected A {
  public:
    A* geta() {
      return static_cast<A*>(this);
    };

    static B* fromA(A* a) {
      return static_cast<B*>(a);
    };
};

int main() {
  B b;

  // Does not even compile
  //std::cout << static_cast<A*>(&b);

  // works like charm
  std::cout << b.geta() << '\n';

  // works also in the reverse direction,although it needs a static method
  std::cout << B::fromA(b.geta()) << '\n';
};

我承认这不是很漂亮。我的测试(使用更复杂的代码)显示它可以正常工作,但是我仍然不确定。

这是有效的C ++代码和正确的做法吗?

iCMS 回答:启用非公共继承的技巧

从概念上讲,getA很好。 B正在选择在其中公开A。可以简化为return this;,不需要强制转换。

我对fromA有所保留,因为这意味着所有A都是B,这可能不是正确的。您应该将fromA的可访问性限制在可以证明所有AB的地方。

可以使用dynamic_cast进行安全下调。

static_cast上的cppreference

本文链接:https://www.f2er.com/1798995.html

大家都在问