有没有办法只在基类中实现一个函数,该函数将返回从中调用它的任何派生类的实例?
答案 0 :(得分:2)
template <class TDerived> class Base
{
TDerived retInstance()
{
return TDerived();
}
};
class Derived : Base<Derived>
{
//class definition here
};
答案 1 :(得分:0)
如上所述,
CRTP(奇怪的重复模板模式)
或Cloneable Pattern。
template <typename Derived>
struct BaseImpl
{
// normal stuff
int foo() const { return 42; }
// CRTP stuff
Derived make_new() const
{
return Derived("test 123");
}
};
#include <string>
struct MyStruct : BaseImpl<MyStruct>
{
std::string value;
MyStruct(std::string const& value) : value(value) {}
};
#include <iostream>
int main()
{
MyStruct a("first");
MyStruct b = a.make_new();
std::cout << a.value << "\n"
<< b.value << "\n";
}
打印
first
test 123
同时查看 Live on Coliru
struct ICloneable
{
virtual const char* whoami() const = 0;
virtual ICloneable* clone() const = 0;
virtual ~ICloneable() throw() {}
};
#include <string>
struct A : ICloneable
{
virtual const char* whoami() const { return "struct A"; }
virtual ICloneable* clone() const { return new A; }
};
struct B : ICloneable
{
virtual const char* whoami() const { return "struct B"; }
virtual ICloneable* clone() const { return new B; }
};
#include <iostream>
#include <typeinfo>
int main()
{
A a;
B b;
ICloneable* aclone = a.clone();
ICloneable* bclone = b.clone();
std::cout << typeid(*aclone).name() << "\n";
std::cout << typeid(*bclone).name() << "\n";
delete aclone;
delete bclone;
}
打印(依赖于编译器):
1A
1B
答案 2 :(得分:0)
如果您选择的语言支持C++ code example返回类型,则可以执行与以下covariant类似的操作:
struct A {
virtual A *make() = 0;
};
struct B : public A {
B *make() override {
return new B{};
}
};
虽然这不符合您在基类中定义一次的标准,但我认为值得一提。