强制派生 class 覆盖一组虚函数中的一个

Force a derived class to override one of a set of virtual functions

给定一个具有一些虚函数的基 class,有人能想出一种方法来强制派生的 class 在编译时恰好覆盖一组虚函数中的一个吗?还是实现相同目标的 class 层次结构的替代表述?

在代码中:

struct Base
{
    // Some imaginary syntax to indicate the following are a "pure override set"
    // [
    virtual void function1(int) = 0;
    virtual void function2(float) = 0;
    // ...
    // ]
};

struct Derived1 : Base {}; // ERROR not implemented
struct Derived2 : Base { void function1(int) override; }; // OK
struct Derived3 : Base { void function2(float) override; }; // OK

struct Derived4 : Base // ERROR too many implemented
{
    void function1(int) override;
    void function2(float) override;
};

我不确定我是否真的有这方面的实际用例,但当我实现一些松散地遵循这种模式的东西时,我想到了这一点,并且认为这是一个值得思考的有趣问题,如果没有别的。

如果您不重写所有抽象虚拟方法,您的 类 将保持抽象。如果要实例化对象,则必须执行所有这些操作。

不,但你可以伪造它。

Base 有非虚拟的 float 和 int 方法,它们转发到一个纯虚拟的 std 变体。

两个助手 类,一个 int 一个 float,实现 std 变体一,将两种情况转发给纯虚拟 int 或 float 实现。

负责处理'wrong type'案子

Derived 继承自一个或另一个 helper,并且仅实现 int 或 float。

struct Base
{
    void function1(int x) { vfunction(x); }
    void function2(float x) { vfunction(x); }
    virtual void vfunction(std::variant<int,float>) = 0;
};
struct Helper1:Base {
    void vfunction(std::variant<int,float> v) final {
      if (std::holds_alternative<int>(v))
        function1_impl( std::get<int>(v) );
    }
    virtual void function1_impl(int x) = 0;
};
struct Helper2:Base {
    void vfunction(std::variant<int,float> v) final {
      if (std::holds_alternative<float>(v))
        function2_impl( std::get<float>(v) );
    }
    virtual void function2_impl(float x) = 0;
};

struct Derived1 : Base {}; // ERROR not implemented
struct Derived2 : Helper1 { void function1_impl(int) override; }; // OK
struct Derived3 : Helper2 { void function2_impl(float) override; }; // OK

这使用 https://en.wikipedia.org/wiki/Non-virtual_interface_pattern -- 接口包含非虚拟方法,可以覆盖其细节以使其行为不同。

如果你害怕人们会覆盖 vfunction 你可以使用私有锁技术,and/or 只需给它起一个像 private_implementation_detail_do_not_implement 这样的名字并相信你的代码审查过程。

Or an alternative formulation of a class hierarchy that achieves the same thing?

一个选择是有一个实现一个功能的中间基础class。

struct Base
{
    virtual ~Base() {};
    virtual void function(int) = 0;
    virtual void function(float) = 0;
};

template <typename T>
struct TBase : Base
{
   virtual void function(T) override {} 
};

struct Derived1 : Base {};
struct Derived2 : TBase<float> { void function(int) override {} };
struct Derived3 : TBase<int> { void function(float) override {} };

int main()
{
   Derived1 d1; // ERROR. Virtual functions are not implemented
   Derived2 d2; // OK.
   Derived3 d3; // OK.
}

请注意,函数在此方法中被命名为 function,而不是 function1function2