返回信息流class B
{
public:
virtual void fun(){printf("fun in B\n");}
void b1(){printf("b1 in B\n");}
};
class D : public B
{
public:
D(){m_d1 =10;}
void fun(){printf("fun in D\n");}
void b1(){printf("b1 in D\n");}
int m_d1;
};
void main()
{
B *pb1 = new B;
D *pd1 = (D*)pb1;
pd1->fun();//问题1,为什么是 fun in B
pd1->b1();//问题2,为什么是 b1 in D
printf("%d\n",pd1->m_d1);////问题3,为什么是 乱码 ;
int a;
((B*)(&a))->b1();//问题4 ,怎么会成功?B* 强转指定要调用B类的b1()吗?强转内存地址有什么变化吗?
}
这是一条镜像帖。来源:北邮人论坛 / cpp / #88395同步于 2015/8/25
该镜像源已超过 30 天没有更新,可能在源站已被删除。
CPP机器人发帖
父类指针和子类指针转换
pingguokaile
2015/8/25镜像同步6 回复
订阅后,新回复会通过你的通知中心匿名送达。
6 条回复
问题一和二主要是你在继承时对于虚函数的处理,问题一有用虚函数,出现这个结果,问题二就是对于函数重新实现
【 在 pingguokaile 的大作中提到: 】
class B
{
public:
virtual...
1、2、3问题都是pd1指向了一个B类对象。
4的话,对象在内存中存的是数据不是函数,函数是一直都有的,不涉及动态成员变量的你可以随便调。((*D)(&a))->m_d1就会错不是1了。
发自「贵邮」
问题二:感觉是在编译的时候确定运行哪个函数,而不是运行的时候,非静态的成员函数在编译时会被替换成外部函数,即pd1的静态类型是D,所以是b1 in D 。
问题一:因为是虚函数,运行时决定运行哪一个函数。
问题四是感觉同问题二,在编译的时候就已经确定了。
问题三:我在Linux下运行输出是0,不是乱码,难道是未定义行为
以上是个人理解,仅供参考。
其实c/c++很多问题,你看下对应的汇编码,自己都能明白。关于问题1,你看下虚函数,虚表的内容,问题2、4你看下编译期间,编译器怎么链接函数的,问题3你看下类在内存中的组织,总之就是3L说的那些。如果你真的想探究下的话,推荐本书《C++反汇编与逆向分析技术揭秘》,看了这本书,你自己就明白你的这些问题了。