VC驿站

 找回密码
 加入驿站

QQ登录

只需一步,快速开始

有编程疑问吗?还请到提问专区发帖提问!
搜索
查看: 3035|回复: 68

《实用C++》第41课 父类对象与子类对象之间的相互转换

  [复制链接]
51_avatar_middle
online_admins Syc 发表于 2018-5-20 00:44:08 | 显示全部楼层 |阅读模式
1、有父子关系的两个类的对象之间能否进行互相转换呢?
答案:由子类对象给父类对象赋值是可以的,俗称大材小用。在赋值的时候会舍弃子类的新增成员,例如:
  1. #include "Student.h"
  2. class CXiaoStudent : public CStudent
  3. {
  4. public:
  5.     int yuwen_score;
  6.     int shuxue_score;
  7.     int english_score;

  8.     CXiaoStudent() : CStudent("zhangsan", 'm', 1001, 20)
  9.     {
  10.         yuwen_score = 2;
  11.         shuxue_score = 0;
  12.         english_score = 0;

  13.         flag_private = 0;
  14.         flag_protected = 0;
  15.     }

  16. private:
  17.     int flag_private;

  18. protected:
  19.     int flag_protected;
  20. };

  21. class CZhongStudent : public CXiaoStudent
  22. {
  23. public:
  24.     int wuli_score;
  25.     int huaxue_score;

  26.     CZhongStudent()
  27.     {
  28.         wuli_score = 0;
  29.         huaxue_score = 0;
  30.     }

  31. public:
  32.     int get_flag_1()
  33.     {
  34.         //return flag_private;
  35.         return flag_protected;
  36.     }
  37. };
复制代码

  1. //赋值操作:
  2. int main(int argc, char* argv[])
  3. {
  4.     CZhongStudent zhong_1;
  5.     zhong_1.wuli_score = 90;
  6.     zhong_1.yuwen_score = 100;
  7.     zhong_1.age = 15;

  8.     CStudent base_stu = zhong_1; //由子类对象给父类对象赋值

  9.     return 0;
  10. }
复制代码


但是,反过来,由父类的对象给子类的对象赋值是不允许的,会出现填不满的不可预知行为。

2、父子类对象转换的实际用途:
在实际的编程过程中,直接进行父子类的对象的相互转换的情况比较少。一般是使用指针来操作。
上节课最后给大家留了一个小作业:
用一个函数来实现一个功能,分别统计全市在校学生的平均年龄。学生包括小学生、中学生、高中生、大学生 等。用一个函数来实现!
不知道大家思考的怎么样?只能用一个函数来实现,还要自动区分是小学生、中学生、高中生或者大学生?要怎么做呢?接下来教大家一种方法。

  1. void average_age(CStudent* p_arr_stud, int n_size)
  2. {
  3.     if (!p_arr_stud || n_size <= 0) return;

  4.     int total_age = 0;
  5.     EStudentType type = p_arr_stud[0].type;
  6.     for (int idx = 0; idx < n_size; ++idx)
  7.     {
  8.         switch (type)
  9.         {
  10.         case EStudentType_Xiao:
  11.             total_age += ((CXiaoStudent*)p_arr_stud)[idx].age;
  12.             break;
  13.         case EStudentType_Zhong:
  14.             total_age += ((CZhongStudent*)p_arr_stud)[idx].age;
  15.             break;
  16.         default:
  17.             break;
  18.         }
  19.     }

  20.     int aver_age = total_age / n_size;
  21.     switch (type)
  22.     {
  23.     case EStudentType_Xiao:
  24.         cout << "小学生的平均年龄是:" << aver_age << endl;
  25.         break;
  26.     case EStudentType_Zhong:
  27.         cout << "中学生的平均年龄是:" << aver_age << endl;
  28.         break;
  29.     default:
  30.         break;
  31.     }
  32. }
复制代码


说明:这里是统计所有类型学生的信息,学生有多种类型,有小学生、中学生、高中生、大学生 等等。以后还可能统计研究生、博士生等等。所以类型很多,如果你针对每种类型的学生都写一个函数进行统计那就非常麻烦了。所以这块我们只写一个函数,还要把全类型都覆盖了,那么我们只能传递各种学生的父类型的指针,因为从子对象往父对象转换是可以的,就是我们之前说的大材小用。但是由父对象往子对象转换往往很危险。另外我们这里面转换的也只是一个指针类型而已,真正子类型的指针指向的那块内存不会因为把指针类型改成父类型了就改变内存结构了。所以我们先通过参数把各种类型的学生都统一成基本的学生类型,之后在函数内部通过事先在父类中定义好的类型来区分参数传进来的到底是哪种子类型,之后强制类型转换就行了。

有的网友会说,你这个强制类型转换不就是从父类型转换到子类型吗?不是很危险吗?你为什么还这样做?刚刚我说过了,指针指向的那块内存本身就是子类型的,之前只不过用另外一种指针指了一下,不会影响那块的内存结构,也不会修改那块的内存内容,所以在函数中再转回来是一点问题没有的。大家明白了吗?我这个例子中用的方法在以后的编程过程中会时不时的用到的,可以解决不少问题,这个思想还是希望大家掌握哦!

3、小作业,刚刚的 average_age 函数我改成这样行不行?
  1. void average_age(CStudent* p_arr_stud, int n_size)
  2. {
  3.     int total_age = 0;
  4.     if (!p_arr_stud || n_size <= 0) return;
  5.     for (int idx = 0; idx < n_size; ++idx)
  6.     {
  7.         total_age += p_arr_stud[idx].age;
  8.     }

  9.     EStudentType type = p_arr_stud[0].type;
  10.     int aver_age = total_age / n_size;
  11.     switch (type)
  12.     {
  13.     case EStudentType_Xiao:
  14.         cout << "小学生的平均年龄是:" << aver_age << endl;
  15.         break;
  16.     case EStudentType_Zhong:
  17.         cout << "中学生的平均年龄是:" << aver_age << endl;
  18.         break;
  19.     default:
  20.         break;
  21.     }
  22. }
复制代码


代码看着很简洁,不知道结果是否正确,大家不妨先试试,如果结果正确那没什么说的,如果结果不争取,那是为什么呢?为什么会出现这样的情况?还请大家课后仔细想想!

第41课免费试看,下载地址回复后可见:
游客,如果您要查看本帖隐藏内容请回复

#######################################################
获得所有教学视频、课件、源代码以及售后答疑详见:
《实用C++》:https://www.cctry.com/thread-275996-1-1.html
VC驿站官方客服QQ:8260671

#######################################################




上一篇:《实用C++》第40课 子类的构造函数与析构函数
下一篇:《实用C++》第42课 多态性与虚函数

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

78_avatar_middle
在线会员 csa 发表于 2018-5-20 08:16:36 | 显示全部楼层
更新好快。谢谢

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

80_avatar_middle
在线会员 zp521 发表于 2018-5-20 08:54:50 | 显示全部楼层
坚持学习!

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

98_avatar_middle
在线会员 tomok 发表于 2018-5-20 10:12:32 | 显示全部楼层
谢谢分享




发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

74_avatar_middle
online_vip08 wssfcn 发表于 2018-5-20 13:09:24 | 显示全部楼层
看看         

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

94_avatar_middle
online_vip08 Mtong 发表于 2018-5-20 23:00:33 | 显示全部楼层
坚持学习!

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

62_avatar_middle
online_vip08 longquan 发表于 2018-5-22 09:36:59 | 显示全部楼层
这个更新速度,真实牛《实用C++》第41课 父类对象与子类对象之间的相互转换

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

09_avatar_middle
online_vip wangxiaohu104 发表于 2018-5-22 11:58:20 | 显示全部楼层
学习下,补下基础

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

79_avatar_middle
在线会员 595084969 发表于 2018-5-23 14:38:16 | 显示全部楼层
支持支持支持支持支持支持

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

95_avatar_middle
在线会员 zjh2008 发表于 2018-5-25 00:07:48 | 显示全部楼层
更新好快。谢谢

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

85_avatar_middle
在线会员 99099800 发表于 2018-5-28 08:38:50 | 显示全部楼层
感谢分享,学习一下。

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

18_avatar_middle
online_vip 听雨声等你笑 发表于 2018-5-28 22:01:06 | 显示全部楼层
学习一下,感谢分享

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

44_avatar_middle
在线会员 a281288098 发表于 2018-5-29 09:21:56 | 显示全部楼层
多谢楼主费心录制.

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

06_avatar_middle
online_vip 1938537171 发表于 2018-5-29 17:42:48 | 显示全部楼层
我爱学习 学习爱我

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

96_avatar_middle
在线会员 Jer808 发表于 2018-5-29 20:36:06 | 显示全部楼层
坚持学习~~~~~

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

82_avatar_middle
在线会员 ha521ha 发表于 2018-5-31 07:46:58 | 显示全部楼层
强啊。。又出新课

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

58_avatar_middle
在线会员 AxiaoA 发表于 2018-5-31 19:33:00 | 显示全部楼层
谢谢分享!

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

75_avatar_middle
在线会员 Sam599 发表于 2018-6-1 18:38:40 | 显示全部楼层
感谢分享,楼主辛苦了!

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

38_avatar_middle
在线会员 Unity 发表于 2018-6-6 21:33:13 | 显示全部楼层
AAAAAAAAAAAAAAAAAAAAAAAAAAAAAA

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

11_avatar_middle
在线会员 wuyantao 发表于 2018-6-9 07:13:19 | 显示全部楼层

感谢分享,谢谢。

发帖求助前要善用论坛搜索功能,那里可能会有你要找的答案;

如果你已经在论坛发帖求助,并且从坛友或者管理的回复中解决了问题,请编辑帖子并把分类改成【已解决】

如何回报帮助你解决问题的坛友?可以给对方加【热心】【驿站币】,加分不会扣除自己的积分,做一个热心并受欢迎的人!

回复 支持 反对

使用道具 举报

您需要登录后才可以回帖 登录 | 加入驿站 qq_login

本版积分规则

QQ|小黑屋|手机版|VC驿站 ( 辽ICP备09019393号tongdun|网站地图wx_jqr

GMT+8, 2018-12-14 14:56

Powered by Discuz! X3.4

© 2009-2018 cctry.com

快速回复 返回顶部 返回列表