《多态性与虚函数》PPT课件.ppt

上传人:tia****nde 文档编号:2737437 上传时间:2019-11-29 格式:PPT 页数:24 大小:949KB
返回 下载 相关 举报
《多态性与虚函数》PPT课件.ppt_第1页
第1页 / 共24页
《多态性与虚函数》PPT课件.ppt_第2页
第2页 / 共24页
《多态性与虚函数》PPT课件.ppt_第3页
第3页 / 共24页
点击查看更多>>
资源描述
第6章 多态性与虚函数, ,多态性的概念 虚函数 纯虚函数与抽象类,数学科学学院:汪小平 wxiaoping325,一、多态性的概念,观察下图,识别其中所使用的元素。,一、多态性的概念,class Node public: void Draw(Graphics,一、多态性的概念,class Shape public: void Draw(Graphics,修改后的类结构(具有抽象类)。,一、多态性的概念,考虑这些图形元素的存储方式。,Shape m_graphN;,一、多态性的概念,Shape* m_graphN; for(int i=0;iDraw(graph);,考虑下面这段程序,它的输出结果可能会是怎样的?,怎么区分指针存储的是哪一类对象地址?,Shape* m_graphN; for(int i=0;iDraw(graph); else (Staff*)m_graphi)-Draw(graph); ,一、多态性的概念,这种编程方式不简洁,程序可读性不强,可以使用C+提供的虚函数,这样使得代码非常简单。,class Shape public: virtual void Draw(Graphics,一、多态性的概念,Shape* m_graphN; for(int i=0;iDraw(graph);,程序在运行时自动识别指针所指向的对象类型,从而调用该对象重写的虚函数,实现运行时的多态性。 多态性分两种:静态多态性和动态多态性。 程序在编译时就能确定应该调用哪个函数,称为静态(或编译时的)多态性,比如:函数重载和运算符重载; 程序在运行过程中才能动态地确定操作所针对的对象,称为动态多态性。这时通过虚函数实现。,二、虚函数,虚函数是动态绑定的基础。 虚函数是非静态的成员函数,静态成员函数、内置成员函数和构造函数都不能说明为虚函数。 声明方式:在函数原型之前写virtual,但函数实现时不能再写。 具有继承性,基类中声明了虚函数,派生类中无论是否说明,同原型函数都自动为虚函数。 虚函数本质:不是重载、屏蔽,而是覆盖。 调用方式:通过基类指针或引用,执行时会 根据指针指向的对象的类类型,决定调用哪个函数。,二、虚函数,#include using namespace std; class B0 /基类B0声明 public: /外部接口 virtual void display() /虚成员函数 cout“B0:display()“endl; ; class B1: public B0 /公有派生 public: void display() cout“B1:display()“endl; ;,二、虚函数,class D1: public B1 /公有派生 public: void display() coutdisplay(); void main() /主函数 B0 b0, *p; /声明基类对象和指针 B1 b1; /声明派生类对象 D1 d1; /声明派生类对象 p= /调用类 ? 函数成员 ,二、虚函数,再谈静态关联与动态关联。,#include #include using namespace std; class Complex public: Complex(); Complex(double); Complex(double, double); operator double(); friend Complex operator +(Complex,int main() Complex c1(3,4),c2(5,-10),c3; double d; d=2.5+c1; coutdendl; c3=c1+c2; coutc3; c3=c1+2.5; coutc3; c3=2.5+c1; coutc3; c3=2.5+3.5; coutc3; return 0; ,二、虚函数,#include #include using namespace std; class Figure /定义基类figure public: void SetValue(double i, double j=0) x = i; y = j; virtual void ShowArea() cout“No area defined for this class.n“; protected: double x, y; ;,二、虚函数,class Triangle : public Figure /定义派生类triangle public: void ShowArea() /定义虚函数的不同版本 cout “Traingle has an area of “ x*0.5*y “.n“; ; class Rectangle : public Figure /定义派生类rectangle public: void ShowArea() /定义虚函数的不同版本 cout “Rectangle has an area of “ x*y “.n“; ;,二、虚函数,class Circle : public Figure /定义派生类circle public : void ShowArea() /定义虚函数的不同版本 cout “Circle has an area of “ 3.14159 * x * x“.“endl; ; int main() Figure* a4; for(int i=0;i4;i+) switch(rand()%4) case 0: ai=new Figure; break;,二、虚函数,case 1: ai=new Triangle; break; case 2: ai=new Rectangle; break; case 3: ai=new Circle; break; ai-SetValue(4,5); for(int i=0;iShowArea(); for(int i=0;i4;i+) delete ai; return 0; ,二、虚函数,特别强调: 使用虚函数实现运行时多态性的关键在于:必须通过基类指针访问这些函数。 一旦一个函数定义为虚函数,无论它传下多少层,一直保持为虚函数。 如果在派生类中没有重写虚函数,则在调用它时,使用最近基类中定义的函数版本。 一般情况下,可将各层次类中具有共性的成员函数(但表现形式不一样的函数)定义为虚函数,某个类特有的成员没有必要说明为虚函数。,二、虚函数,虚析构函数: 何时需要虚析构函数? 当你可能通过基类指针删除派生类对象时;,#include using namespace std; class Point public: Point() cout“Excuting Point destructor.“endl; ; class Circle: public Point public: Circle() cout“Excuting Circle destructor.“endl; ; int main() Point* p=new Circle; delete p; return 0; ,这种普通析构函数可能会产生什么隐患?,二、虚函数,#include using namespace std; class Point public: virtual Point() cout“Excuting Point destructor.“endl; ; class Circle: public Point public: Circle() cout“Excuting Circle destructor.“endl; ; int main() Circle* cp=new Circle; delete cp; Point* p=new Circle; delete p; return 0; ,一个好习惯:无论什么时候,都把析构函数声明为虚析构函数,特别是基类。,三、纯虚函数与抽象类,纯虚函数是定义在基类中的一种成员函数,只给出函数原型,没有任何定义。这样的函数就叫做纯虚函数。纯虚函数的存在,使得任何派生类都必须定义自己的函数版本。否则,在编译时给出错误信息。 纯虚函数定义的一般形式为:,virtual 返回值类型 函数名(形参列表) = 0;,带有纯虚函数的类称为抽象类。 抽象类不能实例出对象,但可以声明指针。,三、纯虚函数与抽象类,抽象类的作用 抽象类为抽象和设计的目的而声明,将有关的数据和行为组织在一个继承层次结构中,保证派生类具有要求的行为。 对于暂时无法实现的函数,可以声明为纯虚函数,留给派生类去实现。比如图类中的Figure的面积、体积、描绘等等。 注意 抽象类只能作为基类来使用。 不能声明抽象类的对象。 构造函数不能是虚函数,析构函数可以是虚函数。,三、纯虚函数与抽象类,#include using namespace std; class B0 /抽象基类B0声明 public: /外部接口 virtual void display( )=0; /纯虚函数成员 ; class B1: public B0 /公有派生 public: void display() cout“B1:display()“endl; /虚函数 ;,三、纯虚函数与抽象类,class D1: public B1 /公有派生 public: void display() coutdisplay(); int main() /主函数 B0 *p; /声明抽象基类指针 B1 b1; /声明派生类对象 D1 d1; /声明派生类对象 p= ,习题,2、5完成在作业本上,
展开阅读全文
相关资源
正为您匹配相似的精品文档
相关搜索

最新文档


当前位置:首页 > 图纸专区 > 课件教案


copyright@ 2023-2025  zhuangpeitu.com 装配图网版权所有   联系电话:18123376007

备案号:ICP2024067431-1 川公网安备51140202000466号


本站为文档C2C交易模式,即用户上传的文档直接被用户下载,本站只是中间服务平台,本站所有文档下载所得的收益归上传人(含作者)所有。装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。若文档所含内容侵犯了您的版权或隐私,请立即通知装配图网,我们立即给予删除!