【问题标题】:Inheritance regardless of input parameters不考虑输入参数的继承
【发布时间】:2018-03-07 06:54:36
【问题描述】:

我想创建接口类,然后从中继承派生类。 不幸的是,可以有多种类型的派生类 - 方法名称相同但输入参数不同。

这是继承类的类图

无论输入参数的类型(和数量!)如何,都可以创建 InterfaceClass 吗?

我想要实现什么 - 拥有多个最终子级 (SpecificWorker1..n),并且每个子级都必须实现名称为“buildRequest”的方法,但它是自己的一组输入参数。

谢谢。

【问题讨论】:

  • 你试过了吗?尝试不会比问这个问题花费更多的时间,编译器会回答你
  • 是的.. 当我声明“void buildRequest(std::list inputList)”时它不起作用,因为 SpecificWorker1 没有从 InterfaceClass 覆盖 buildRequest()。

标签: c++ class inheritance arguments virtual-functions


【解决方案1】:

我不知道你为什么要这样做。但是您可以使用可变参数模板尝试此解决方案。只是想回答这个问题:

无论类型如何都可以创建 InterfaceClass(和 计数!)的输入参数?

template <typename Head, typename ...Tail>
class InterfaceClass
{
private:
    static void buildRequest() {};

public:
    virtual ~InterfaceClass() = default;
    virtual void buildRequest(Head h, Tail  ...t) = 0;
};

template <typename Head, typename ...Tail>
class DefaultWorker : public InterfaceClass <Head, Tail...>
{
public:

    virtual void buildRequest(Head h, Tail  ...t) = 0;

};

class SpecificWorker1 : public DefaultWorker <std::list<int>, int>
{
public:

    void buildRequest(std::list<int> h, int g = 0) override
    {
        std::cout << "Hello from SpecificWorker1. list size: " << h.size() << std::endl;
    }

};

class SpecificWorker2 : public DefaultWorker <int, float>
{
public:
    void buildRequest(int h, float f) override
    {
        std::cout << "Hello from SpecificWorker2. " << h << " " << f << std::endl;
    }
};

class SpecificWorker3 : public DefaultWorker <int, float, std::string>
{
public:
    void buildRequest(int h, float f, std::string comment) override
    {
        std::cout << "Hello from SpecificWorker3. int: " << h << " float:  " << f << " comment: " << comment << std::endl;
    }
};

int main()
{
    SpecificWorker2 e;
    e.buildRequest(1, 1.1);

    std::list<int> list{ 1, 2, 3 };
    SpecificWorker1 c;
    c.buildRequest(list);

    SpecificWorker3 d;
    d.buildRequest(1, 1.1, "this is a comment");

    system("pause");

}

输出:

【讨论】:

  • 是的,我们发现可变参数模板是最佳解决方案。尽管看起来并不容易,但它确实有效。 :D 也许我们会那样做。
【解决方案2】:

不,你所有不同的 buildrequest 重载都是单独的方法,除了 SpecificWorker3 之外,你所有的类都是抽象的,因为它们没有实现没有参数的版本。

你真正想要达到什么目的?当你的接口没有参数时,你将如何将参数传递给你的重载?

【讨论】:

    【解决方案3】:

    你不能按照你想要的方式去做。您可以创建结构的继承层次结构,其中层次结构中的每个子项都包装不同类型的参数。但是,这将完全违背最初拥有接口和继承的目的,因为原始接口的每个实现都必须能够处理各种输入。

    说实话,你的设计有些可疑,你不应该这样做。你想达到什么目的?

    【讨论】:

    • 我只想拥有尽可能多的不同子代(SpecificWorker 1..n),但每个子代都必须以自己的方式实现名为“buildRequest”的方法。跨度>
    • @ZdenoPavlik 如果这些buildRequest 方法没有相同的签名,您打算如何通过接口调用它们?请记住,虚函数的意义在于在不知道您实际拥有哪个实现的情况下调用它们。
    • 如果我知道如何轻松做到这一点,我就不会发布这个问题了。
    • @ZdenoPavlik 我的意思是你不能。您需要重新评估您的设计。也许将参数传递给 SpecificWorker 类的构造函数并存储它们?然后他们都可以用相同的无参数签名实现buildRequest
    • @MilesBudnek 幸运的是,这还没有设计出来,只是在设计中。我们正在考虑它。是的,通过构造函数传递参数是可能的。也可以创建一些 DTO 结构并仅传输其中的所有数据。但我们都不喜欢它。我原以为这种方法行不通,但在得出最终结论之前,我想从这里的人们那里找到不同的意见......
    猜你喜欢
    • 1970-01-01
    • 2018-11-20
    • 1970-01-01
    • 1970-01-01
    • 2011-08-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-08-12
    相关资源
    最近更新 更多