0

我有一个基类,它有两个从它派生的子类。

class A {};
class B : public A {};
class C : public A {};

我有另一个类,它有一个使用向量指向 A 类成员集合的指针,如下所示:

vector<A*> *m_collection;

我所做的是创建 B 或 C 类的对象并使用 push_back 将它们添加到集合中:

B *myb = new B();
m_collection->push_back(myb);

然后我遍历集合并尝试使用'typeid'进行检查,但它总是返回基类(A)。不可能知道确切的类型吗?

谢谢!

4

2 回答 2

4

首先,不太可能有理由使用 new 动态创建向量。简单地说:

vector<A*> m_collection;

然后你需要给你的基类一个或两个虚函数。虚拟析构函数将是一个好的开始:

class A {
   public:
     virtual ~A() {}
};

没有它,您将无法安全地编写如下代码:

m_collection.push_back( new B );
delete m_collection[0];

这样做还将启用运行时类型信息。然而,开启typeid并不是 C++ 喜欢你使用 RTTI 的方式——你应该使用dynamic_cast

m_collection.push_back( new B );    // or new A or new C
if ( C * c = dynamic_cast<C *>( m_collection[0] ) ) {
   c->CFunc():  // function in C
}
else if ( B * b = dynamic_cast<B *>( m_collection[0] ) ) {
   b->BFunc():  // function in B
}
else if ( A * a = dynamic_cast<A *>( m_collection[0] ) ) {
   a->AFunc():  // function in A
}
else {
  throw "unknown type";
}

然而,总的来说,最好使用虚函数机制进行调度,而不是 RTTI。

于 2010-02-09T17:47:56.257 回答
0

Wrt typeid,您需要在基类 (A) 中有一个虚函数(vtable 通常位于 std::type_info 结构附近),然后您必须取消引用该对象,即typeid(*b).

于 2010-02-09T17:50:07.470 回答