幻灯片 1

Similar documents
Microsoft PowerPoint - 第06讲_继承.ppt [兼容模式]

OOP with Java 通知 Project 4: 4 月 18 日晚 9 点 关于抄袭 没有分数

OOP with Java 通知 Project 4: 4 月 19 日晚 9 点

C 1 # include <stdio.h> 2 int main ( void ) { 4 int cases, i; 5 long long a, b; 6 scanf ("%d", & cases ); 7 for (i = 0;i < cases ;i ++) 8 { 9

2013 C 1 # include <stdio.h> 2 int main ( void ) 3 { 4 int cases, a, b, i; 5 scanf ("%d", & cases ); 6 for (i = 0;i < cases ;i ++) 7 { 8 scanf ("%d %d

幻灯片 1

Chapter12 Derived Classes

OOP with Java 通知 Project 3: 3 月 29 日晚 9 点 4 月 1 日上课

Microsoft PowerPoint - 8. 运算符重载 Operator Overloading.pptx

无类继承.key

Microsoft PowerPoint - 04-Inheritance.ppt

Strings

C++_Lecture

untitled

OOP with Java 通知 Project 4: 5 月 2 日晚 9 点

软件工程文档编制

Microsoft PowerPoint - 6. 用户定义类型User-defined Datatypes.ppt [兼容模式]

第七讲 继承与多态

c_cpp

Microsoft PowerPoint - string_kruse [兼容模式]

Strings

新版 明解C++入門編

面向对象的程序设计 : 抽象 继承和多态 Dongke Sun (Southeast University) C++ Programming and Algorithms April 12, / 38

untitled

Microsoft Word - 新1-12.doc

FY.DOC

Microsoft PowerPoint - L17_Inheritance_v4.pptx

NOWOER.OM m/n m/=n m/n m%=n m%n m%=n m%n m/=n 4. enum string x1, x2, x3=10, x4, x5, x; 函数外部问 x 等于什么? 随机值 5. unsigned char *p1; unsigned long *p

C/C++语言 - C/C++数据

C++ 程序设计 实验 2 - 参考答案 MASTER 2017 年 5 月 21 日 1

untitled

Microsoft PowerPoint - CPP-Ch Print.ppt [兼容模式]

第3章.doc

提问袁小兵:

北京大学

OOP with Java 通知 Project 3 提交时间 3 月 29 日晚 9 点 Piazza Project 2 投票

Microsoft PowerPoint - 第07讲_多态1.ppt [兼容模式]

untitled

<4D F736F F F696E74202D20B5DA3032BDB25FC0E0BACDB6D4CFF3312E BBCE6C8DDC4A3CABD5D>

Microsoft PowerPoint - 10 模板 Template.pptx

Microsoft Word - ch04三校.doc

OOP with Java 通知 Project 4: 4 月 19 日晚 9 点

提纲 1 联编与多态性 2 用虚函数实现多态 3 虚函数的工作原理 4 纯虚函数与抽象类 5 总结与思考 Dongke Sun (Southeast University) C++ Programming and Algorithms April 12, / 36

OOP with Java 通知 Project 4: 5 月 2 日晚 9 点

OOP with Java 通知 Project 4: 5 月 2 日晚 9 点

运算符重载 为什么要 运算符重载 那些运算符可以重载, 哪些不可以 如何实现运算符重载 实现方式 : 成员函数与非成员函数 类型转换 怎样实现对象与基本数据类型数据的运算 2

Microsoft Word cppFinalSolution.doc

OOP with Java 通知 Project 4: 推迟至 4 月 25 日晚 9 点

Microsoft PowerPoint - 3. 函数Functionl.ppt [兼容模式]

Microsoft Word - 把时间当作朋友(2011第3版)3.0.b.06.doc

程序设计语言及基础

Modeling & Simulation 数学原理 物理规律和程序设计的综合 Magic Fluids Heart Simulator Dongke Sun (Southeast University) C++ Programming and Algorithms April 23,

2013 C 1 #include <stdio.h> 2 int main(void) 3 { 4 int cases, i; 5 long long a, b; 6 scanf("%d", &cases); 7 for (i = 0; i < cases; i++) 8 { 9 scanf("%

保母人員丙級應檢資料第二部份 doc

Microsoft PowerPoint - 4. 数组和字符串Arrays and Strings.ppt [兼容模式]

Microsoft Word - 第3章.doc

詞 彙 表 編 號 詞 彙 描 述 1 預 約 人 資 料 中 文 姓 名 英 文 姓 名 身 份 證 字 號 預 約 人 電 話 性 別 2 付 款 資 料 信 用 卡 別 信 用 卡 號 信 用 卡 有 效 日 期 3 住 房 條 件 入 住 日 期 退 房 日 期 人 數 房 間 數 量 入

OOP with Java 通知 Project 2 提交时间 : 3 月 14 日晚 9 点 另一名助教 : 王桢 学习使用文本编辑器 学习使用 cmd: Power shell 阅读参考资料

Microsoft Word - 把时间当作朋友(2011第3版)3.0.b.07.doc

1 1 大概思路 创建 WebAPI 创建 CrossMainController 并编写 Nuget 安装 microsoft.aspnet.webapi.cors 跨域设置路由 编写 Jquery EasyUI 界面 运行效果 2 创建 WebAPI 创建 WebAPI, 新建 -> 项目 ->

Microsoft Word - 第7章 类与对象.docx

ASP.NET实现下拉框二级联动组件

内部明电

chap07.key

SDK 概要 使用 Maven 的用户可以从 Maven 库中搜索 "odps-sdk" 获取不同版本的 Java SDK: 包名 odps-sdk-core odps-sdk-commons odps-sdk-udf odps-sdk-mapred odps-sdk-graph 描述 ODPS 基

C 1

運算子多載 Operator Overloading

《C语言程序设计》教材习题参考答案

Guava学习之Resources

今天 年春季号 总 92 期

*

( ) / / / / / / /

(Microsoft Word - 8\244T\244\362\277\337\272]\244W\265L\246W.doc)

Microsoft Word - 專家本色 doc


但, 你 应 该 听 过 我 们 走 在 大 路 上 这 首 歌, 或 许 还 知 道 革 命 人 永 远 是 年 轻 那 支 歌 ; 并 且, 几 乎 可 以 肯 定, 你 在 戴 红 领 巾 的 那 阵, 必 然 唱 过 牛 儿 还 在 山 坡 吃 草, 放 牛 的 却 不 知 道 哪 儿 去

2 临 终 助 念 答 问 序 临 终 关 怀, 由 佛 门 净 宗 古 来 祖 师 大 德 提 倡 助 念 往 生, 现 今 已 渐 为 社 会 大 众 所 重 视, 在 台 湾, 台 大 长 庚 等 各 大 医 院, 也 都 设 有 助 念 室 ; 大 陆 上 许 多 道 场, 也 有 专 为

校园之星

Microsoft Word - 澎湖田調報告-宏達組9804.doc

<4D F736F F F696E74202D FA8BEA861B8EAB7BDBEE3A658BB50C0B3A5CE28B773A6CBA5AB29>


之 原 則 及 國 防 部 訂 頒 國 軍 列 管 國 有 不 動 產 提 供 非 軍 方 單 位 使 用 處 理 原 則 規 定 不 符, 仍 應 以 出 租 方 式 辦 理 惟 可 就 偏 遠 地 區 提 供 官 兵 金 融 水 電 服 務 使 用 部 分, 研 議 降 低 租 金 標 準, 報

chineseall

釋禪波羅蜜次第法門

证券代码: 证券简称:锦江股份 公告编号:【】

1700 装 卸 搬 运 7645 装 卸 搬 运 服 务 2100 建 筑 7410 工 程 服 务 11% 装 卸 搬 运 服 务, 是 指 使 用 装 卸 搬 运 工 具 或 者 人 力 畜 力 将 货 物 在 运 输 工 具 之 间 装 卸 现 场 之 间 或 者 运 输 工 具 与 装 卸

前 言 教 育 无 小 事, 它 成 就 着 学 生 的 未 来 作 为 教 师, 他 们 无 时 无 刻 不 在 关 注 着 学 生 的 成 长 学 生 的 未 来 学 生 就 像 一 朵 含 苞 待 放 的 花 朵, 需 要 老 师 们 的 细 心 呵 护, 给 学 生 需 要 的 东 西, 而

《盗墓笔记》 南派三叔/著

平 凡 足 迹 李 本 川 作 者 为 中 国 科 学 院 海 洋 研 究 所 研 究 员,1935 年 生, 山 东 荣 成 人 我 今 年 63 岁 了 大 前 年 丈 夫 和 儿 子 在 一 个 月 内 先 后 离 开 了 人 世, 女 儿 又 已 出 嫁, 现 在 是 孑 然 一 身 我 是

<CFFBB7D1D5DFD0D0CEAAD1A72E6D7073>

独立学院建设与发展


团 学 要 闻 我 校 召 开 共 青 团 五 届 九 次 全 委 ( 扩 大 ) 会 议 3 月 17 日, 我 校 共 青 团 五 届 九 次 全 委 ( 扩 大 ) 会 议 在 行 政 办 公 楼 五 楼 会 议 室 举 行, 校 团 委 委 员 各 院 ( 系 ) 团 委 书 记 校 学 生

山东建筑大学学分制管理规定(试行)

ebook55-13

1.5招募说明书(草案)

C++ 程序设计 OJ9 - 参考答案 MASTER 2019 年 6 月 7 日 1

全国计算机技术与软件专业技术资格(水平)考试

<4D F736F F F696E74202D20332D322E432B2BC3E6CFF2B6D4CFF3B3CCD0F2C9E8BCC6A1AAD6D8D4D8A1A2BCCCB3D0A1A2B6E0CCACBACDBEDBBACF2E707074>

Microsoft Word - CPE考生使用手冊 docx

Transcription:

信息科学技术学院 程序设计实习 郭炜微博 http://weibo.com/guoweiofpku http://blog.sina.com.cn/u/3266490431 刘家瑛微博 http://weibo.com/pkuliujiaying 1

信息科学技术学院 程序设计实习 郭炜刘家瑛 继承和派生 ( 教材 P215) 2

继承和派生的概念 继承 : 在定义一个新的类 B 时, 如果该类与某个已有的类 A 相似 ( 指的是 B 拥有 A 的全部特点 ), 那么就可以把 A 作为一个基类, 而把 B 作为基类的一个派生类 ( 也称子类 ) 3

继承和派生的概念 派生类是通过对基类进行修改和扩充得到的 在派生类中, 可以扩充新的成员变量和成员函数 派生类一经定义后, 可以独立使用, 不依赖于基类 4

继承和派生的概念 派生类拥有基类的全部成员函数和成员变量, 不论是 private protected public 在派生类的各个成员函数中, 不能访问基类中的 private 成员 5

需要继承机制的例子 所有的学生都有的共同属性 : 姓名学号性别成绩所有的学生都有的共同方法 ( 成员函数 ): 是否该留级是否该奖励 6

需要继承机制的例子 而不同的学生, 又有各自不同的属性和方法研究生导师系大学生系中学生竞赛特长加分 7

需要继承机制的例子 如果为每类学生都从头编写一个类, 显然会有不少重复的代码, 浪费 比较好的做法是编写一个 学生 类, 概括了各种学生的共同特点, 然后从 学生 类派生出 大学生 类, 中学生 类, 研究生类 8

需要继承机制的例子 CStudent CHighSchoolStudent CUndergraduateStudent CGraduatedStuden

派生类的写法 class 派生类名 :public 基类名 { 10

class CStudent { private: string sname; int nage; public: bool IsThreeGood() { void SetName( const string & name ) { sname = name; } //... class CUndergraduateStudent: public CStudent { private: int ndepartment; public: bool IsThreeGood() {... // 覆盖 bool CanBaoYan() {... // 派生类的写法是 : 类名 : public 基类名 11

class CGraduatedStudent:public CStudent { private: int ndepartment; char szmentorname[20]; public: int CountSalary() {... 12

派生类对象的内存空间 派生类对象的体积, 等于基类对象的体积, 再加上派生类对象自己的成员变量的体积 在派生类对象中, 包含着基类对象, 而且基类对象的存储位置位于派生类对象新增的成员变量之前 class CBase { int v1,v2; class CDerived:public CBase { int v3; 13

继承实例程序 : 学籍管理 (P228) #include <iostream> #include <string> using namespace std; class CStudent { private: string name; string id; // 学号 char gender; // 性别,'F' 代表女,'M' 代表男 int age; public: void PrintInfo(); void SetInfo( const string & name_,const string & id_, int age_, char gender_ ); string GetName() { return name; } 14

class CUndergraduateStudent:public CStudent {// 本科生类, 继承了 CStudent 类 private: string department; // 学生所属的系的名称 public: void QualifiedForBaoyan() { // 给予保研资格 cout << qualified for baoyan << endl; } void PrintInfo() { CStudent::PrintInfo(); // 调用基类的 PrintInfo cout << Department: << department <<endl; } void SetInfo( const string & name_,const string & id_, int age_,char gender_,const string & department_) { CStudent::SetInfo(name_,id_,age_,gender_); // 调用基类的 SetInfo department = department_; } 15

void CStudent::PrintInfo() { cout << "Name:" << name << endl; cout << "ID:" << id << endl; cout << "Age:" << age << endl; cout << "Gender:" << gender << endl; } void CStudent::SetInfo( const string & name_,const string & id_, int age_,char gender_ ) { name = name_; id = id_; age = age_; gender = gender_; } 16

int main() { } CUndergraduateStudent s2; s2.setinfo( Harry Potter, 118829212,19, M, Computer Science ); cout << s2.getname() << ; s2.qualifiedforbaoyan (); s2.printinfo (); return 0; 17

输出结果 : Harry Potter qualified for baoyan Name:Harry Potter ID:118829212 Age:19 Gender:M Department:Computer Science 18

信息科学技术学院 程序设计实习 郭炜微博 http://weibo.com/guoweiofpku http://blog.sina.com.cn/u/3266490431 刘家瑛微博 http://weibo.com/pkuliujiaying 1

信息科学技术学院 程序设计实习 郭炜刘家瑛 继承关系和复合关系 (P231) 2

类之间的两种关系 继承 : 是 关系 基类 A,B 是基类 A 的派生类 逻辑上要求 : 一个 B 对象也是一个 A 对象 复合 : 有 关系 类 C 中 有 成员变量 k,k 是类 D 的对象, 则 C 和 D 是复合关系 一般逻辑上要求 : D 对象是 C 对象的固有属性或组成部分 3

继承关系的使用 写了一个 CMan 类代表男人 后来又发现需要一个 CWoman 类来代表女人 CWoman 类和 CMan 类有共同之处 CMan 就让 CWoman 类从 CMan 类派生而来, 是否合适? 是不合理的! 因为 一个女人也是一个男人 从逻辑上不成立! CWoman 4

继承关系的使用 好的做法是概括男人和女人共同特点, 写一个 CHuman 类, 代表 人, 然后 CMan 和 CWoman 都从 CHuman 派生 CHuman CWoman CMan 5

复合关系的使用 几何形体程序中, 需要写 点 类, 也需要写 圆 类 class CPoint { double x,y; class CCircle:public CPoint { double r; 6

复合关系的使用 几何形体程序中, 需要写 点 类, 也需要写 圆 类, 两者的关系就是复合关系 ---- 每一个 圆 对象里都包含 ( 有 ) 一个 点 对象, 这个 点 对象就是圆心 class CPoint { double x,y; friend class CCircle; // 便于 Ccirle 类操作其圆心 class CCircle { double r; CPoint center; 7

复合关系的使用 如果要写一个小区养狗管理程序, 需要写一个 业主 类, 还需要写一个 狗 类 而狗是有 主人 的, 主人当然是业主 ( 假定狗只有一个主人, 但一个业主可以有最多 10 条狗 ) 8

复合关系的使用 class CDog; class CMaster { CDog dogs[10]; class CDog { CMaster m; 9

10

11

复合关系的使用 class CDog; class CMaster { CDog dogs[10]; class CDog { CMaster m; 循环定义! 12

复合关系的使用 另一种写法 : 为 狗 类设一个 业主 类的成员对象 ; 为 业主 类设一个 狗 类的对象指针数组 class CDog; class CMaster { CDog * dogs[10]; class CDog { CMaster m; 13

复合关系的使用 凑合的写法 : 为 狗 类设一个 业主 类的对象指针 ; 为 业主 类设一个 狗 类的对象数组 class CMaster; //CMaster 必须提前声明, 不能先 // 写 CMaster 类后写 Cdog 类 class CDog { CMaster * pm; class CMaster { CDog dogs[10]; 14

复合关系的使用 正确的写法 : 为 狗 类设一个 业主 类的对象指针 ; 为 业主 类设一个 狗 类的对象指针数组 class CMaster; //CMaster 必须提前声明, 不能先 // 写 CMaster 类后写 Cdog 类 class CDog { CMaster * pm; class CMaster { CDog * dogs[10]; 15

1 基类 / 派生类同名成员 与 Protected 关键字 郭炜刘家瑛 北京大学程序设计实习

基类和派生类有同名成员的情况 class base { int j; public: int i; void func(); class derived : public base{ public: int i; void access(); void func(); 2

基类和派生类有同名成员的情况 class base { int j; public: int i; void func(); class derived : public base{ public: int i; void access(); void func(); 3

void derived::access() { j = 5; i = 5; //error // 引用的是派生类的 i base::i = 5; // 引用的是基类的 i func(); // 派生类的 base::func(); // 基类的 } derived obj; obj.i = 1; obj.base::i = 1; Obj 占用的存储空间 Base::j Base::i i Note: 一般来说, 基类和派生类不定义同名成员变量 4

访问范围说明符 基类的 private 成员 : 可以被下列函数访问 基类的成员函数 基类的友员函数 基类的 public 成员 : 可以被下列函数访问 基类的成员函数 基类的友员函数 派生类的成员函数 派生类的友员函数 其他的函数 5

访问范围说明符 : protected 基类的 protected 成员 : 可以被下列函数访问 基类的成员函数 基类的友员函数 派生类的成员函数可以访问当前对象的基类的保护成员 6

保护成员 class Father { private: int nprivate; // 私有成员 public: int npublic; // 公有成员 protected: int nprotected; // 保护成员 class Son : public Father { void AccessFather () { npublic = 1; // ok; nprivate = 1; // wrong nprotected = 1; // OK, 访问从基类继承的 protected 成员 Son f; f.nprotected = 1; //wrong, f 不是当前对象 } 7

int main(){ Father f; Son s; f.npublic = 1; // Ok s.npublic = 1; // Ok f.nprotected = 1; // error f.nprivate = 1; // error s.nprotected = 1; //error s.nprivate = 1; // error return 0; } 8

1 派生类的构造函数 郭炜刘家瑛 北京大学程序设计实习

派生类的构造函数 派生类对象包含基类对象执行派生类构造函数之前, 先执行基类的构造函数派生类交代基类初始化, 具体形式 : 构造函数名 ( 形参表 ): 基类名 ( 基类构造函数实参表 ) { } 2

派生类的构造函数 class Bug { private : int nlegs; int ncolor; public: int ntype; Bug (int legs, int color); void PrintBug () { class FlyBug: public Bug { // FlyBug 是 Bug 的派生类 int nwings; public: FlyBug(int legs, int color, int wings); 3

Bug::Bug( int legs, int color) { nlegs = legs; ncolor = color; } // 错误的 FlyBug 构造函数 : FlyBug::FlyBug (int legs, int color, int wings) { nlegs = legs; // 不能访问 ncolor = color; // 不能访问 ntype = 1; // ok nwings = wings; } // 正确的 FlyBug 构造函数 : FlyBug::FlyBug (int legs, int color, int wings):bug(legs, color) { nwings = wings; } 表达式中可以出现 : FlyBug 构造函数的参数 4

int main() { FlyBug fb ( 2,3,4); fb.printbug(); fb.ntype = 1; fb.nlegs = 2 ; // error.nlegs is private return 0; } 5

FlyBug fb (2,3,4); 在创建派生类的对象时, 需要调用基类的构造函数 : 初始化派生类对象中从基类继承的成员 在执行一个派生类的构造函数之前, 总是先执行基类的构造函数

调用基类构造函数的两种方式 显式方式 : 派生类的构造函数中 基类的构造函数提供参数 derived::derived(arg_derived-list):base(arg_base-list) 隐式方式 : 派生类的构造函数中, 省略基类构造函数时派生类的构造函数, 自动调用基类的默认构造函数 派生类的析构函数被执行时, 执行完派生类的析构函数后, 自动调用基类的析构函数

class Base { public: int n; Base(int i):n(i) { cout << "Base " << n << " constructed" << endl; } ~Base() { cout << "Base " << n << " destructed" << endl; } class Derived:public Base { public: Derived(int i):base(i) { cout << "Derived constructed" << endl; } ~Derived() { cout << "Derived destructed" << endl; } int main() { Derived Obj(3); return 0; } 8

输出结果 : Base 3 constructed Derived constructed Derived destructed Base 3 destructed 9

包含成员对象的派生类的构造函数 class Skill { public: Skill(int n) { } class FlyBug: public Bug { int nwings; Skill sk1, sk2; public: FlyBug(int legs, int color, int wings); FlyBug::FlyBug( int legs, int color, int wings): Bug(legs, color), sk1(5), sk2(color) { nwings = wings; } 表达式中可以出现 : FlyBug 构造函数的 参数, 常量 10

创建派生类的对象时, 执行派生类的构造函数之前 : 调用基类的构造函数 初始化派生类对象中从基类继承的成员 调用成员对象类的构造函数 初始化派生类对象中成员对象 执行完派生类的析构函数后 : 调用成员对象类的析构函数 调用基类的析构函数 析构函数的调用顺序与构造函数的调用顺序相反

信息科学技术学院 程序设计实习 郭炜微博 http://weibo.com/guoweiofpku http://blog.sina.com.cn/u/3266490431 刘家瑛微博 http://weibo.com/pkuliujiaying 1

public 继承的赋值兼容规则 7

public 继承的赋值兼容规则 class base { class derived : public base { base b; derived d; 1) 派生类的对象可以赋值给基类对象 b = d; 2) 派生类对象可以初始化基类引用 base & br = d; 3) 派生类对象的地址可以赋值给基类指针 base * pb = & d; 如果派生方式是 private 或 protected, 则上述三条不可行 8

直接基类和间接基类 9

直接基类与间接基类 类 A 派生类 B, 类 B 派生类 C, 类 C 派生类 D, 类 A 是类 B 的直接基类 类 B 是类 C 的直接基类, 类 A 是类 C 的间接基类 类 C 是类 D 的直接基类, 类 A B 是类 D 的间接基类 A B C D 10

直接基类与间接基类 在声明派生类时, 只需要列出它的直接基类 派生类沿着类的层次自动向上继承它的间接基类 A B C D 派生类的成员包括 派生类自己定义的成员 直接基类中的所有成员 所有间接基类的全部成员 11

#include <iostream> using namespace std; class Base { public: int n; Base(int i):n(i) { cout << "Base " << n << " constructed" << endl; } ~Base() { cout << "Base " << n << " destructed" << endl; } 12

class Derived:public Base { public: Derived(int i):base(i) { cout << "Derived constructed" << endl; } ~Derived() { cout << "Derived destructed" << endl; } 13

class MoreDerived:public Derived { public: MoreDerived():Derived(4) { cout << "More Derived constructed" << endl; } ~MoreDerived() { cout << "More Derived destructed" << endl; } int main() { MoreDerived Obj; return 0; } 14

输出结果 : Base 4 constructed Derived constructed More Derived constructed More Derived destructed Derived destructed Base 4 destructed 15