C++:从静态方法调用继承的静态方法

C++ : Calling inherited static method from static method

本文关键字:静态方法 继承 调用 C++      更新时间:2023-10-16

考虑以下抽象类AbstractEngine

class AbstractEngine {
    static void init();
    static std::string getName();
};

并考虑以下 2 个实现器类:

class Engine1 : public AbstractEngine  {   
    static std::string getName();
};
class Engine2 : public AbstractEngine {   
    static std::string getName();
};

并且,init()函数应根据类的类型调用正确的getName()

void AbstractEngine::init() {
    std::cout << getName() << std::endl;
}

例如,如果我调用Engine1::init(),我希望它调用Engine1::getName()而不是AbstractEngine::getName()

我怎样才能真正AbstractEngine::init()调用getName()的正确实现?

您可以使用

CRTP,即将AbstractEngine做一个模板类,然后在继承时,从AbstractEngine<EngineN>继承:

template <typename T> 
class AbstractEngine {
public:
    static void init() {
        std::cout << T::getName() << std::endl;  
    }
};
class Engine1 : public AbstractEngine<Engine1>  {   
public:
    static std::string getName() { return "Engine1"; }
};
class Engine2 : public AbstractEngine<Engine2> {  
public:
    static std::string getName() { return "Engine2"; }
};

现场演示


如果你还需要一些动态多态行为,你可以创建一个通用的非模板基类:

class AbstractEngine {
    //I assume you would have some virtual functions here
};
template <typename T> 
class AbstractEngineImpl : public AbstractEngine {
public:
    static void init() {
        std::cout << T::getName() << std::endl;  
    }
};
class Engine1 : public AbstractEngineImpl<Engine1>  {   
public:
    static std::string getName() { return "Engine1"; }
};
class Engine2 : public AbstractEngineImpl<Engine2> {  
public:
    static std::string getName() { return "Engine2"; }
};

getName()方法不应是静态的。也不是init()方法。

您正在尝试获得多态行为,但使用静态函数。这没有任何意义。根据定义,多态行为与特定的对象实例相关联 - 但静态函数没有关联的实例。

如果你想要多态行为(如你标记所建议的那样),请考虑这个重新设计:

class AbstractEngine {
    virtual void init();
    virtual std::string getName();
};
class Engine1 : public AbstractEngine  {   
    std::string getName() override;
};
class Engine2 : public AbstractEngine {   
    std::string getName() override;
};