第19课 - 专题三经典问题解析

1. 当多态遇见对象数组会发生什么?

#include <cstdlib>

#include <iostream>

using namespace std;

class Parent

{

protected:

int i;

public:

virtual void f()

{

cout<<"Parent::f"<<endl;

}

};

//sizeof(Parent) = 8,int i占四个字节,虚函数占四个字节。

class Child : public Parent

{

protected:

int j;

public:

Child(int i, int j)

{

this->i = i;

this->j = j;

}

void f()

{

cout<<"i = "<<i<<" "<<"j = "<<j<<endl;

}

};

//sizeof(child) = 12,继承来int i四个字节,自己又定义四个字节,虚函数表四个字节

int main(int argc, char *argv[])

{

Parent* p = NULL;

Child* c = NULL;

Child ca[3] = {Child(1, 2), Child(3, 4), Child(5, 6)};

p = ca;  //赋值兼容性原理 ,数组名就是第一个元素的地址  i=1,j=2

c = ca;  //i=1,j=2

cout<<hex<<p+1<<endl;

p->f();  //f是个重写函数 ,发生了多态,要根据实际的情况来判定用的那个函数。

//这行有误

c->f();

p++; //指向数组中的第二个对象

c++;

//   p->f();

//  c->f();

cout << "Press the enter key to continue ...";

cin.get();

return EXIT_SUCCESS;

}

不要将多态应用于数组。指针运算是通过指针的类型进行的。多态通过虚函数表实现的。

指针运算是编译器根据指针的类型来进行的,多态是在运行的时候通过虚函数表查询来进行的。这两种实现方式是不同的。多态是程序运行的时候动态的查找函数的。

l  多态与指针的混搭的结果

我们看ca[0]的长度是12,只有12个字节长度的指针才能与它合理搭配。

结论:

不要在数组上使用多态。

2. 为什么没有讲解多重继承

C++在语法上是支持多重继承的。

l  被实际开发经验抛弃的多继承

工程开发中真正意义上的多继承是几乎不被使用的。

多重继承带来的代码复杂性远多于其带来的便利。

多重继承对代码的维护性上的影响是灾难性的。

再设计方法上,任何多继承都可以用单继承来代替。

3. 多继承复杂性示例

#include <cstdlib>

#include <iostream>

using namespace std;

class Object

{

protected:

int d;

public:

void f()

{

cout<<"Object::f"<<endl;

}

};

class P1 : public Object

{

protected:

int i;

};

class P2 : public Object

{

protected:

int j;

};

class Child : public P1, public P2

{

public:

Child(int i, int j)

{

this->d = 0; //二义性 ,child不是直接继承的object,而是间接的,有了两个d

this->i = i;

this->j = j;

}

void print()

{

cout<<"i = "<<i<<" "<<"j = "<<j<<endl;

}

};

int main(int argc, char *argv[])

{

Child c(1, 2);

c.print();

c.f();  //同样有二义性,不知道是从哪里来的,继承只能感受到,直接的父类。

cout << "Press the enter key to continue ...";

cin.get();

return EXIT_SUCCESS;

}

在只有单继承的系统中,类之间的继承关系为一棵树。

在引入多重继承的系统中,类之间的继承关系呈现为一张图。

l  C++中对多继承二义性的解决方案

虚继承:

为了解决从不同途径继承来的同名数据成员造成的二义性问题,可以将共同的基类设置为虚基类。这是从不同的路径继承过来的同名数据成员在内存中就有一个拷贝。

这样做,实际上是治标不治本,只会使得在工程中更加麻烦。

class P1 : virtual public Object

{

protected:

int i;

};

class P2 : virtual public Object

{

protected:

int j;

};

在实际的工程中的类是成百上千的,所以我们实际工作中尽量少使用多继承。虚函数是很占用空间的,不写又会怀疑。

4. C++是否有Java中接口的概念

绝大多数面向对象的语言都不支持多继承。

绝大多数面向对象语言都支持接口的概念。

C++中没有接口的概念。

C++中可以使用虚函数来实现接口

class Interface

{

public:

virtual void func1() = 0;

virtual void func2(int i) = 0;

virtual void func3(int i, int j) = 0;

};

实际的工程经验证明。多重继承接口不会带来二义性和复杂性等问题。多重继承可以通过精心设计用单继承和接口来代替。

接口只是一个功能说明,而不是功能实现。子类需要根据功能说明定义功能实现。

#include <cstdlib>

#include <iostream>

using namespace std;

class Interface1  //第一个接口

{

public:

virtual void print() = 0;

virtual int add(int i, int j) = 0;

};

struct Interface2  //第二个接口

{

virtual int add(int i, int j) = 0;

virtual int minus(int i, int j) = 0;

};

class Child : public Interface1, public Interface2

{

public:

void print()

{

cout<<"Child::print"<<endl;

}

int add(int i, int j)

{

return i + j;

}

int minus(int i, int j)

{

return i - j;

}

};

int main(int argc, char *argv[])

{

Child c;

c.print();

cout<<c.add(3, 5)<<endl;

cout<<c.minus(4, 6)<<endl;

Interface1* i1 = &c;

Interface2* i2 = &c;

cout<<i1->add(7, 8)<<endl;

cout<<i2->add(7, 8)<<endl;

cout << "Press the enter key to continue ...";

cin.get();

return EXIT_SUCCESS;

}

运行结果:

Child::print

8

-2

15

15

专题三中的多态是实现设计模式的基本技术!

转载于:https://www.cnblogs.com/free-1122/p/11336236.html

C++--第19课 - 专题三经典问题解析相关推荐

  1. 人教版三年级下册计算机课教案,人教版三年级下册19课教案

    人教版三年级下册19课教案 (7页) 本资源提供全文预览,点击全文预览即可全文预览,如果喜欢文档就下载吧,查找使用更方便哦! 15.9 积分 课题: Unit 4 Do you like candy? ...

  2. 新手入门刷题(专题三)暴力枚举

    新手入门刷题(专题三)暴力枚举--->持续更新 4.14 统计方形(数据加强版) 题目描述 有一个 n×m 方格的棋盘,求其方格包含多少正方形.长方形(不包含正方形). 输入格式 一行,两个正整 ...

  3. 计算机信息继续考试 d组教材,无为县“备好课”专题培训考核小结

    无为县2008--2009学年度"备好课"专题培训,注重能力考核,过程性考查和结果性考核相结合,有效地调动了参训教师远程学习的主动性,促进了集体备课制度的建设和校本教研文化建设. ...

  4. 免费技术直播:唐宇迪带你一节课了解机器学习经典算法

    常常有小伙伴在后台反馈:机器学习经典算法有哪些? 自学难度大又没有效果,该怎么办? CSDN为了解决这个难题,联合唐宇迪老师为大家带来了一场精彩的直播[一节课掌握机器学习经典算法-线性回归模型].本次 ...

  5. 语言ppt课件猜拳_八年级语文上册第22课 孟子三章讲解及课件下载

    八年级语文上册 [第一单元] 八年级语文上册第1课<消息二则>讲解及PPT课件下载 八年级语文上册第2课<首届诺贝尔奖颁发>讲解及PPT课件下载 八年级语文上册第3课<& ...

  6. 3w最简单led灯电路图_Mixly 第19课 光感应灯——光敏电阻使用

    第19课  光感应灯--光敏电阻使用 光敏电阻器又叫光感电阻,是利用半导体的光电效应制成的一种电阻值随入射光的强弱而改变的电阻器:入射光强,电阻减小,入射光弱,电阻增大.光敏电阻器一般用于光的测量.光 ...

  7. Nehe第19课 粒子系统

    源代码链接 #include<windows.h> // Windows的头文件 #include <gl/glew.h> // 包含最新的gl.h,glu.h库 #inclu ...

  8. 大学计算机说课稿,【实用】信息技术说课稿三篇

    [实用]信息技术说课稿三篇 作为一名默默奉献的教育工作者,常常需要准备说课稿,说课稿有助于顺利而有效地开展教学活动.那么说课稿应该怎么写才合适呢?以下是小编收集整理的信息技术说课稿4篇,仅供参考,大家 ...

  9. 第19课 微信小程序安装使用mpvue脚手架

    第19课 微信小程序安装使用mpvue脚手架: 详情地址:http://mpvue.com/mpvue/quickstart/ 安装前检查环境: 安装脚手架之前需要电脑已安装node与npm 首先按住 ...

  10. 第19课 编排节目顺序

    第19课 编排节目顺序 [教材分析] 本课主要介绍广播和接收消息的应用.广播与接收是Scratch的学习难点,也是创作丰富作品的基础知识之一.教材以马戏团的节目表演为引入,小猫.小猴和大象按广播的消息 ...

最新文章

  1. [每日一题] OCP1z0-047 :2013-08-14 如何理解USING INDEX?...................................41
  2. unable to contact ip driver
  3. 绘制机械图c语言编程,求用C语言绘制机械三视图程序?
  4. Android被逼学习例子2
  5. mysql maxtmptables_mysql的tmp_table_size和max_heap_table_size
  6. 亲手搭建一个基于Asp.Net WebApi的项目基础框架1
  7. 使用docker registry建立私有镜像仓库
  8. Chrome浏览器可以修改特定页面背景色吗?Chrome浏览器修改特定页面背景色的方法
  9. ubuntu mate 开机自动启动ssh服务
  10. 牛客小白月赛9: div.2 A(线性筛)
  11. iOS测试技巧:GPX文件修改经纬度
  12. win10 安装 HP LaserJet P1108 教程
  13. 驾考网上理论刷学时防每20分钟弹框
  14. 手机OTG是什么功能,怎样使用?
  15. java+es+nested_Elasticsearch中的关联查询。Nested类型介绍及查询原理。。
  16. Setuptools(Python打包工具)
  17. [《南国雪下》闲笔记事集]2010年12月15日 记雪
  18. 关于flask-sqlalchemy同字段多条件的过滤方法
  19. [Jenkins]jenkins配置163邮箱做邮件发送
  20. 轻松解决yum源不能正常下载的四种方式

热门文章

  1. NLP学习04--长短期记忆网络LSTM
  2. JQuery的一些简单使用
  3. GitHub配置SSH key
  4. Android Dialog的简单说明
  5. slqite3库查询数据处理方式_从数据仓库到百万标签库,精细化数据管理,这么做就够了...
  6. 网络推手团队_辛8工作室,被列入经营异常名单!工作室发声明解释!二子爷喊话辛8:你能强大过马云吗?达少太忙没有时间玩!团队断水断粮式野外生存!...
  7. java增删改查控制台_在控制台中输入增删改查 (初学者)
  8. c#服务器后台搭建_微信影视小程序搭建拆解:第一课,影视小程序简介,搭建影视小程序的整体流程...
  9. linux apache 配置视频教程,《Linux服务器配置视频教程》ubuntu centos apache iptables 后盾网向军老师主讲[WMV]...
  10. 可以悬浮在屏幕的搜题软件_悬浮窗搜题app下载-悬浮窗搜题预约 安卓版v1.0.0-PC6安卓网...