在C++中实现子类中的静态方法重载

Gha*_*nPL 4 c++ oop static templates class

我有这样的事情:

class Base
{
  public:
    static int Lolz()
    {
      return 0;
    }
};

class Child : public Base
{
  public:
    int nothing;
};

template <typename T>
int Produce()
{
  return T::Lolz();
}
Run Code Online (Sandbox Code Playgroud)

Produce<Base>();
Produce<Child>();
Run Code Online (Sandbox Code Playgroud)

两者都返回0,这当然是正确的,但不需要.反正是否在第二个类中强制执行Lolz()方法的显式声明,或者在使用时可能会抛出编译时错误Produce<Child>()

或者是不好的OO设计,我应该做一些完全不同的事情?

编辑:

我基本上想要做的是做出类似这样的工作:

Manager manager;

manager.RegisterProducer(&Woot::Produce, "Woot");
manager.RegisterProducer(&Goop::Produce, "Goop");

Object obj = manager.Produce("Woot");
Run Code Online (Sandbox Code Playgroud)

或者更一般地说,外部抽象工厂不知道它正在生成的对象的类型,因此可以添加新类型而无需编写更多代码.

you*_*ung 7

有两种方法可以避免它.实际上,这取决于你想说什么.

(1)将Produce()作为Base类的接口.

template <typename T>
int Produce()
{
  return T::Lolz();
}
class Base
{
    friend int Produce<Base>();

protected:
    static int Lolz()
    {
        return 0;
    }
};

class Child : public Base
{
public:
    int nothing;
};

int main(void)
{
    Produce<Base>(); // Ok.
    Produce<Child>(); // error :'Base::Lolz' : cannot access protected member declared in class 'Base'
}
Run Code Online (Sandbox Code Playgroud)

(2)使用模板专业化.

template <typename T>
int Produce()
{
  return T::Lolz();
}
class Base
{
public:
    static int Lolz()
    {
        return 0;
    }
};

class Child : public Base
{
public:
    int nothing;
};

template<>
int Produce<Child>()
{
    throw std::bad_exception("oops!");
    return 0;
}

int main(void)
{
    Produce<Base>(); // Ok.
    Produce<Child>(); // it will throw an exception!
}
Run Code Online (Sandbox Code Playgroud)