也许我误解了继承如何在这里工作,但这是我的问题:
我有一个类Option,以及一个派生自它的类RoomOption。我有另一个课室,里面有一个shared_ptrs的矢量。在主要内容中,我向该向量添加了一个RoomOption。然后,使用typeid()我检查类型,它告诉我它的选项。根据我的阅读,typeid应该返回派生类型,而shared_ptrs不会导致切片,所以我不确定我做错了什么。
以下是代码:
Room.h:
vector<shared_ptr<Option> > options;
void addOption(shared_ptr<Option>);
shared_ptr<Option> getOption(int);
Room.cpp:
void Room::addOption(shared_ptr<Option> option){
options.push_back(option);
}
shared_ptr<Option> Room::getOption(int i){
return options[i];
}
主:
shared_ptr<Room> outside(new Room(0, "", ""));
outside->addOption(shared_ptr<RoomOption>(new RoomOption(0, "Go inside", hallway)));
cout<<typeid(player->getRoom()->getOption(0)).name().get()<<endl;
//This line prints "class std::tr1::shared_ptr<class Option>
在我看来,可能在添加或获取选项时,由于返回/参数类型,RoomOption会被转换为选项。如果是这种情况那么我应该如何存储多种类型的矢量?或者我错了吗? = \
答案 0 :(得分:15)
对于多态(对于具有至少一个虚函数的类)和非多态类型,typeid
的工作方式不同:
如果类型是多态的,则表示它的相应typeinfo
结构在运行时确定(vtable指针通常用于此目的,但这是一个实现细节)
如果类型不是多态的,则在编译时确定相应的typeinfo结构
在你的情况下,你实际上有一个多态类Option
,但shared_ptr<Option>
itsef根本不是多态的。它基本上是一个容纳Option*
的容器。 Option
和shared_ptr<Option>
之间绝对存在 no 继承关系。
如果要获取真实类型,首先需要使用Option* shared_ptr<Option>::get()
从容器中提取实际指针:
Option * myPtr = player->getRoom()->getOption(0).get();
cout << typeid(*myPtr).name(); << endl;
或者(完全相同):
Option& myPtr = *player->getRoom()->getOption(0);
cout << typeid(myPtr).name(); << endl;
答案 1 :(得分:1)
shared_ptr<Option>
指向的对象类型是其值的一部分,而不是其类型。所以这行代码被打破了:
cout<<typeid(player->getRoom()->getOption(0)).name()<<endl;
你想要这个:
cout<<typeid(player->getRoom()->getOption(0).get()).name()<<endl;
或者也许:
cout<<typeid(*(player->getRoom()->getOption(0))).name()<<endl;
typeid
的作用是告诉你传递给它的事物的实际类型。你传递了shared_ptr<Option>
。它不会查看对象内部以查看它包含的内容。
答案 2 :(得分:1)
首先获取shared_ptr的typeid。
然后你应该使用dynamic_cast而不是typeid。 E.g:
if (dynamic_cast<RoomOption*>(player->getRoom()->getOption(0).get()) != 0){
cout << "Its a RoomOption!" << endl;
}