有条件地继承纯基类

时间:2017-01-14 00:29:04

标签: c++ templates inheritance c++14

假设我有以下类定义

struct base {
  virtual int f() = 0;
};

struct A: public base {
  int f() final { return 1; }
};

struct B: public base {
  int f() final { return 2; }
};

是否可以将AB转换为带有bool参数的模板,该参数指定是否继承base?我有一些用例,它们需要或者不需要提供公共接口的基类。

假设AB有很多成员函数,因此重复实现将是乏味的。但sizeof(A)sizeof(B)很小。

3 个答案:

答案 0 :(得分:4)

不确定

template <bool> struct A
{
    // ...
};

template <> struct A<true> : base
{
    // ...
};

(请注意,如果可以避免冗余,您可以从A<true>派生A<false>。)

例如:

template <bool> struct A
{
    void f() { std::cout << "A::f called\n"; }
};

template <> struct A<true> : A<false>, base
{
    void f() override { A<false>::f(); }
};

int main()
{
    A<false> a1;
    A<true> a2;
    a1.f();
    a2.f();
    static_cast<base&>(a2).f();
}

答案 1 :(得分:3)

我提出了我正在寻找的更直接的方法,没有代码重复。

struct base {
  virtual int f() = 0;
};

struct empty_base { };

template <bool Inherit>
struct A final: public std::conditional_t<Inherit,base,empty_base> {
  int f() { return 1; }
};

答案 2 :(得分:1)

由于您使用的是纯基类,因此当您调用A::f()时优化器将避免虚函数调用时,区别不应该是重要的,因为永远不会有实现不同版本的派生类f()

如果您不打算继承class A final : base以避免必须为每个功能添加A,也可以执行final