[英]c++ how to implement const static members in derived classes
在C ++中,我有几个继承自抽象超类的类。 子类具有共享相同名称type
的静态属性,但是当然具有不同的值。 我的问题是实现此目标的最佳方法是什么,每种实现的利弊是什么?
PS:这里有一些相关的讨论,但是大多数都没有解释为什么不应该使用下面的方法(对我的机器有效)1。 此外,方法2中的子类方法不是静态的,因此我们将不得不获取实例来调用它们。
方法1:超类中的uinitialized const static
class Abstract {
public:
const static int type;
};
class C1: public Abstract {
public:
const static int type = 1;
};
class C2 : public Abstract {
public:
const static int type = 2;
};
方法2:使用虚拟函数代替变量
class Abstract {
public:
virtual int get_type() = 0;
};
class C1: public Abstract {
public:
int get_type() {return 1;}
};
class C2 : public Abstract {
public:
int get_type() {return 2;}
};
我不知道的其他方法...
编辑:
正如下面提到的一些答案/评论,我试图在运行时识别实际类型。 但是我真的不能想到更好的设计。
Abstract=EduInst
, Abstract=EduInst
是教育机构的Abstract=EduInst
, C1=Univ
, C2=College
等。我有一个std::map<Key, EduInst*>
存储所有机构,这些机构是在运行时根据用户输入生成的。 有时我只需要在Univ
或College
上进行操作。 什么是实现此目标的好方法?
首先警告:
继承描述了与基类的“某种”关系。 仅当您将不同种类的对象存储在同一容器中,这些种类的对象绝对共享相同的接口,并且不需要对任何派生类进行任何特殊处理时(例如,当您是对象的使用者时),这才有意义不需要知道其类型)。
此外,如果您只有几种相同的事物,并且在编译时就可以知道这些事物,那么使用继承可能是一个错误。
如果您的继承对象必须向客户端标识其实际类型,则这进一步证明了继承是错误的解决方案-因为现在您将使用代码来查找代码,这是一个坏主意(不可测试,并且有责任)程序处于意想不到的状态时会出错)。
此外,如果您有不同的对象但需要存储在同一容器中,则boost::variant
可能是您正在寻找的解决方案。 然后,您可以使用boost::static_visitor
对变量中的对象执行操作。 这样做的好处是绝对是类型安全的,并且编译器不会让您忘记处理类型。
说了这么多...
方法1无效,因为如果您已经具有派生类的类型,则将始终获得基类的类型。
方法2可以使用,但是很可怕,并且表明设计已损坏。
您不能有“虚拟”静态成员。
方法一是查找类的“类型”属性,第二种方法是查找实例的“类型”属性。
换句话说:使用第一个,您需要了解该类; 要使用第二个,您需要知道实例。
在您都不知道的地方编写代码是不可能的。
请注意,如果您在基类的函数中使用type
,则一种方法可能会给您带来意想不到的结果。
例如,
class Abstract
{
public:
int get_type() const { return type; }
};
// ...
C1 c;
std::cout << c.get_type();
将输出0,因为那是Abstract::type
的值。
第二种方法的一种变体是如果您牺牲了另一个成员的空间,则可以避免使用虚函数:
class Abstract {
public:
// ...
int get_type() const { return type; }
protected:
Abstract(int t) : type(t) {}
private:
int type;
};
class C1: public Abstract {
public:
C1() : Abstract(1) {}
};
class C2 : public Abstract {
public:
C2() : Abstract(2) {}
};
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.