【发布时间】:2011-12-18 12:57:14
【问题描述】:
我的程序需要处理不同种类的“笔记”:NoteShort、NoteLong... 不同种类的笔记应该以不同的方式显示在 GUI 中。我定义了这些笔记的基类,称为NoteBase。
我将这些注释存储在 XML 中;我有一个从 XML 文件中读取数据并将笔记数据存储在vector<NoteBase *> list 中的类。然后我发现我无法获取自己的类型,因为它们已经转换为NoteBase *!
虽然if(dynamic_cast<NoteLong *>(ptr) != NULL) {...} 可能有效,但它真的太丑了。实现函数以NoteShort * 或NoteLong * 作为参数不起作用。那么,有什么好办法解决这个问题呢?
更新:谢谢大家的回复。我认为这也不应该发生——但它确实发生了。我以另一种方式实现了它,现在它正在工作。但是,据我记得,我确实在NoteBase 中声明了(纯)虚函数,但忘记在派生类的标题中再次声明它。我想这就是导致问题的原因。
更新 2(重要): 我从 C++ Primer 中找到了这句话,可能对其他人有帮助:
有时更令人惊讶的是, 即使在基指针或 引用实际上绑定到派生对象:
Bulk_item bulk; Item_base *itemP = &bulk; // ok: dynamic type is Bulk_item Bulk_item *bulkP = itemP; // error: can't convert base to derived编译器无法在编译时知道特定的 转换在运行时实际上是安全的。编译器只看 在指针或引用的静态类型处确定是否 转换是合法的。在那些情况下,当我们知道转换 从基础到派生是安全的,我们可以使用 static_cast (Section 5.12.4,第183) 覆盖编译器。或者,我们可以请求一个在运行时检查的转换,方法是使用 dynamic_cast,在第 18.2.1 节(第 773 页)中有介绍。
【问题讨论】:
-
这是一个非常离题的话题,只是出于好奇:还有什么其他原因你实际上需要有几个类来实现你的目标?
-
当然因为它们有许多共同的属性,但有时应该区别对待。观看this 30 秒,你就会知道我现在在做什么......
标签: c++ inheritance polymorphism