第四十九课、多态的概念和意义
一、多态初体验
1、函数重写的回顾
(1)、父类中被重写的函数依然会被继承给子类
(2)、子类中重写的函数将会覆盖父类中的函数
(3)、通过作用域分辨符(::)可以访问到父类中的函数
2、面向对象中期望的行为
(1)、根据实际对象的类型判断如何调用重写函数
(2)、若父类指针(引用)指向
A、指向父类对象则调用父类中定义的函数
B、指向子类对象则调用子类中定义的重写函数
3、面向对象中多态的概念
(1)、根据实际的对象类型决定函数调用的具体目标
(2)、同样的调用语句在实际运行时有多种不同的表现形态
4、c++直接支持多态的概念
(1)、通过使用virtual关键字对多态进行支持
(2)、被virtual声明的函数被重写后具有多态的特性
(3)、被virtual声明的函数叫做虚函数
#include<iostream> using namespace std; class Parent { public: virtual void print()//仅仅比上一课的代码多了一个virtual { cout << "I'm Parent" << endl; } }; class Child : public Parent { public: void print() { cout << "I'm Child" << endl; } }; void how_to_print(Parent* p) { p->print();//运行的时候才确定要调用哪个函数 } int main() { Parent p; Child c; how_to_print(&p);//期望I'm Parent,实际I'm Parent how_to_print(&c);//期望I'm Child,实际I'm Child return 0; }
二、多态的意义
1、在程序运行过程中展现出动态的特性
2、函数重写必须实现多态,否则没有意义
3、多态是面向对象组件化程序设计的基础特性
三、理论中的概念
1、静态联编
(1)、在编译期就能确定具体函数的调用(如重载函数)
2、动态联编
(1)、在程序运行后才能确定具体的函数调用(如重写函数)
#include <iostream> #include <string> using namespace std; class Parent { public: virtual void func() { cout << "void func()" << endl; } virtual void func(int i) { cout << "void func(int i) : " << i << endl; } virtual void func(int i, int j) { cout << "void func(int i, int j) : " << "(" << i << ", " << j << ")" << endl; } }; class Child : public Parent { public: void func(int i, int j) { cout << "void func(int i, int j) : " << i + j << endl; } void func(int i, int j, int k) { cout << "void func(int i, int j, int k) : " << i + j + k << endl; } }; void run(Parent* p) { p->func(1, 2); // 展现多态的特性 // 动态联编,运行时才确定调用哪个函数 } int main() { Parent p; p.func(); // 静态联编 p.func(1); // 静态联编 p.func(1, 2); // 静态联编 cout << endl; Child c; c.func(1, 2); // 静态联编 cout << endl; run(&p); run(&c);
cout << endl;
return 0; }
四、小结
1、函数重写只能发生在父类和子类之间
2、根据实际对象的类型确定具体调用的函数
3、virtual关键字是c++中支持多态的唯一方式
4、被重写的虚函数可表现出多态的特性