如何从基类指针调用派生类方法? [英] How to call derived class method from base class pointer?
问题描述
我有类似于下面的类结构
class A
{
public:
A(void);
〜A(void);
void DoSomething(int i)
{
std :: cout< Hello A<< i<< std :: endl;
}
};
class B:public A
{
public:
B(void);
〜B(void);
void DoSomething(int i)
{
std :: cout< Hello B<< i<< std :: endl;
}
};
class Ad:public A
{
public:
Ad(void);
〜Ad(void);
};
class Bd:public B
{
public:
Bd(void);
〜Bd(void);
};
我想将一个派生类的实例存储在一个容器strong> A * ,然后遍历每个实例的容器和调用方法。
#includeAh
#includeBh
#includeAd.h
#includeBd.h
#include< map&
int main(int argc,char ** argv)
{
std :: map< int,A *>对象映射;
objectmap [1] = new Ad();
objectmap [2] = new Bd();
for(std :: map< int,A *> :: iterator itrobject = objectmap.begin();
itrobject!= objectmap.end(); itrobject ++)
{
itrobject-> second-> DoSomething(1);
}
return 0;
}
上述代码生成以下输出。
您好A1
您好A1
我期待的地方
你好A1
在 B 中隐藏 A ,并且因为我存储 A 指针,我不会期望对象切片(并且在调试器中查看对象指针表明该对象没有切片)。
你好B1
我已经尝试投放和动态投放指向 B 的指针,但会将 Bd
有没有任何方法调用 B :: DoSomething ,而不将指针投射到 Bd ?如果没有,如果我有许多 B 的派生类(例如 Bda , Bdb , Bdc 等)是否有一些方法可以使用RTTI来知道将哪个派生类转换为?
解决方案c> DoSomething() a
virtual
函数,以获取您之后的多态行为:virtual void DoSomething(int i){...
编辑:显示你不需要在每个子类中实现虚函数:
#include< ; iostream>
class A {
public:
virtual void print_me(void){
std :: cout< I'm A< std :: endl;
}
virtual〜A(){}
};
class B:public A {
public:
virtual void print_me(void){
std :: cout< I'm B< std :: endl;
}
};
class C:public A {
};
int main(){
A a;
B b;
C c;
A * p =& a;
p-> print_me();
p =& b;
p-> print_me();
p =& c;
p-> print_me();
return 0;
}
输出:
我是A
我是B
我是A
I have a class structure similar to the following
class A { public: A(void); ~A(void); void DoSomething(int i) { std::cout << "Hello A" << i << std::endl; } }; class B : public A { public: B(void); ~B(void); void DoSomething(int i) { std::cout << "Hello B" << i << std::endl; } }; class Ad : public A { public: Ad(void); ~Ad(void); }; class Bd : public B { public: Bd(void); ~Bd(void); };
I want to store instances of the derived classes in a container (standard map) as a collection of A*, then iterate through the container and call methods for each instance.
#include "A.h" #include "B.h" #include "Ad.h" #include "Bd.h" #include <map> int main(int argc, char** argv) { std::map<int,A*> objectmap; objectmap[1] = new Ad(); objectmap[2] = new Bd(); for (std::map<int,A*>::iterator itrobject = objectmap.begin(); itrobject!=objectmap.end();itrobject++) { itrobject->second->DoSomething(1); } return 0; }
The above code produces the following output.
Hello A1 Hello A1
Where I was expecting
Hello A1 Hello B1
because I was expecting DoSomething in B to hide DoSomething in A, and because I am storing A pointers, I would expect no object slicing (and looking at the object pointer in the debugger shows that the object has not been sliced).
I have tried down casting and dynamic casting the pointer to B, but it slices away the data members of Bd.
Is there any way to call B::DoSomething without casting the pointer to Bd? And if not, if I have many derived classes of B (e.g. Bda, Bdb, Bdc etc), is there some way to use RTTI to know which derived class to cast it to?
解决方案You need to make
DoSomething()
avirtual
function in both classes to get the polymorphic behavior you're after:virtual void DoSomething(int i) { ...
EDIT: to show you don't need to implement virtual functions in every sub class:
#include <iostream> class A { public: virtual void print_me(void) { std::cout << "I'm A" << std::endl; } virtual ~A() {} }; class B : public A { public: virtual void print_me(void) { std::cout << "I'm B" << std::endl; } }; class C : public A { }; int main() { A a; B b; C c; A* p = &a; p->print_me(); p = &b; p->print_me(); p = &c; p->print_me(); return 0; }
outputs:
I'm A I'm B I'm A
这篇关于如何从基类指针调用派生类方法?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!