以下两段程序的输出是什么?
程序1:
#include "stdio.h" class Base { public: int Bar(char x) { return (int)(x); } virtual int Bar(int x) { return (2 * x); } }; class Derived : public Base { public: int Bar(char x) { return (int)(-x); } int Bar(int x) { return (x / 2); } }; int main(void) { Derived Obj; Base *pObj = &Obj; printf("%d,", pObj->Bar((char)(100))); printf("%d,", pObj->Bar(100)); }
分析:
答案:100 50
Derived Obj;
Base *pObj = &Obj;
printf("%d,", pObj->Bar((char)(100)))
printf("%d,", pObj->Bar(100));
第一个Bar(char)是非虚函数,因此是静态绑定,静态绑定是指指针指向声明时的对象,pObj声明时为Base类,因此调用的是Base类的Bar(char)
第二个Bar(char)是虚函数,因此是动态绑定,动态绑定是指指针指向引用的对象,pObj引用Derived对象,因此调用的是Derived类的Bar(int)
程序2:
#include <iostream> using namespace std; class animal{ protected: int age; public: virtual void print_age(void) = 0; }; class dog : public animal{ public: dog(){ this->age = 2; } ~dog(){} virtual void print_age(void){ cout << "wang. my age=" << this->age << endl; } }; class cat:public animal{ public : cat(){ this->age = 1; } ~cat(){} virtual void print_age(void){ cout << " Miao,my age= " << this->age << endl; } }; int main(void){ cat kitty; dog jd; animal *pa; int *p = (int *)(&kitty); int *q = (int *)(&jd); //cout << p[1] << endl; //cout << q[1] << endl; p[1] = q[1]; pa = &kitty; pa->print_age(); return 0; }
分析:
答案:Miao, my age =2
int*p = (int*)(&kitty);
int*q = (int*)(&jd);
p和q是分别指向kitty和jd两个对象的首地址,因为类Cat和Dog都包含虚函数,所以kitty和jd两个对象均包含一个虚函数表,并通过一个指针指向它,p[0]和q[0]就是该虚函数表指针,而p[1]和q[1]则为该对象的数据成员即age的值,p[1]=1,q[1]=2
p[1] = q[1]=2;
kitty的age被修改为2,
animal *pa;
pa = &kitty;
pa->print_age();
pa指针声明时的类型为基类animal,它指向派生类kitty对象,典型的多态特性,则pa的静态类型为animal,动态类型为cat。
而print_age()是虚函数,因此是动态绑定,动态绑定指向是动态类型的成员,因此调用的是kitty的成员函数print_age(),
cout << " Miao,my age= " << this->age << endl;
此时age=2.