实验内容 1. 某计算机硬件系统,为了实现特定的功能,在某个子模块设计了 ABC 三款芯片用于 数字计算。各个芯片的计算功能如下: A 芯片:计算两位整数的加法(m+n)、计算两位整数的减法(m-n) B 芯片:计算两位整数的加法(m+n)、计算两位整数的乘法(m*n) C 芯片:计算两位整数的加法(m+n)、计算两位整数的除法(m/n) 为 ABC 三个芯片分别定义类,描述上述芯片的功能,并在 main 函数中测试这三个类。 (提示:利用类的继承和派生,抽象出共有属性和操作作为基类。)

解答:

下面给出该题目的一个cpp文件

代码:

 #include<iostream>
using namespace std;
class Z{
public:
void createZ(int x0,int y0);
void jia();
private:
int m;
int n;
};
void Z::createZ(int x0,int y0){
m=x0;
n=y0;
}
void Z::jia(){
cout<<"相加的结果:"<<m+n<<endl;
} class A:public Z{
public:
void createA(int x0,int y0);
void jian();
private:
int m1;
int n1;
};
void A::createA(int x0,int y0){
createZ(x0,y0);
m1=x0;
n1=y0;
}
void A::jian(){
cout<<"相减之后的答案:"<<m1-n1 <<endl;
}
class B:public Z{
public:
void createB(int x0,int y0);
void cheng();
private:
int m2;
int n2;
};
void B::createB(int x0,int y0){
createZ(x0,y0);
m2=x0;
n2=y0;
}
void B::cheng(){
cout<<"相乘的结果:"<<m2*n2<<endl; //从A继承到B呢
}
class C:public Z{
public:
void createC(int x0,int y0);
void chu();
private:
int m3;
int n3;
};
void C::createC(int x0,int y0){
createZ(x0,y0);
m3=x0;
n3=y0;
}
void C::chu(){
cout<<"相除的结果:"<<m3/n3<<endl; //从A继承到B呢
} int main(){ A a;
B b;
C c;
a.createA(,);
a.jia();
a.jian();
cout<<endl;
c.createC(,);
c.chu();
c.jia();
cout<<endl;
b.createB(,);
b.cheng();
b.jia(); return ;
}

运行截图:

该题总结:

2. 定义一个车(vehicle)基类,具有数据成员 maxspeed, weight(均为 int 型), 函数 成员 run(), stop(),由此派生出自行车(bicycle)类、汽车(motorcar)类。其中, bicycle 类 新增数据成员高度(height), motorcar 类新增数据成员座位数(seatnum)属性。再从 bicycle
第 2 页/共 4 页
和 motorcar 派生出摩托车(motorcycle)类,并在主程序中测试这个类。(每个类都要求定 义构造函数和析构函数) (提示: ① 注意把 vehicle 设置为虚基类; ② run(), stop()函数体,通过输出字符串 run, stop 简单模拟。 )

解答:

代码是一个cpp文件:

 #include<iostream>
using namespace std;
class vehicle{
public:
vehicle(int m,int w):maxspeed(m),weight(w){
}
~vehicle(){
}
void run(){
cout<<"正在启动中。"<<endl;
}
void stop(){
cout<<"停下汽车!"<<endl;
} private:
int maxspeed;
int weight ; };
class bicycle:virtual public vehicle{
public:
bicycle(int w,int m,int h):vehicle(w,m),height(h){
} ~bicycle(){
}
void getht(){
cout<<"高度:"<<height<<endl;
}
private:
int height;
};
class motorcar:virtual public vehicle{
public:
motorcar(int w,int m,int s):vehicle(w,m),seatnum(s){
}
~motorcar(){
}
void getsm(){
cout<<"座位数量:"<<seatnum<<endl;
}
private:
int seatnum;
};
class motorcycle:public bicycle,public motorcar{
public:
motorcycle(int w,int m,int h,int s):vehicle(w,m),bicycle(w,m,h),motorcar(w,m,s){ }
~motorcycle(){
}
}; int main(){
motorcycle m(,,,);
m.getht();
m.getsm();
m.run();
m.stop();
return ;
}
//构造函数的写法是这个程序带给我的最大收获。
//派生类的构造函数需要写出基类的构造函数,并可以根据参数的不同来进行修改fuzhi

运行截图:

3. 基于「实验 4 类和对象-2」中设计并实现的类 Fraction,创建派生类 iFraction,用以 描述如下形式的分数:

要求: (1) 更新 Fraction 类 为 Fraction 类编写运算符+、-、*、/重载函数,实现在 main 函数中直接用+、-、 *、/进行 Fraction 类运算。 (2)设计并实现派生 iFraction 类 ① 为派生类 iFraction 定义构造函数,实现 iFraction 对象的初始化 ② 为派生类 iFraction 增加一个成员函数,用于在屏幕上显示 iFraction 对象 (3)设计一个普通函数 convertF()用于对 iFraction 类对象进行规范化处理。(*选做*)
(提示:把 convertF()设计为 Fraction 类和 iFraction 类的友元函数) 例如:(更多情形请自行考虑)
5/3
→ 1
2 /3
(4)以多文件结构方式编写(fraction.h, fraction.cpp, ifraction.h, ifraction.cpp, main.cpp)

解答:

代码如下:

1.fraction.h

 #ifndef FRACTION_H
#define FRACTION_H
class fraction{
public:
fraction(int a=,int b=);
// fraction(fraction &f);
~fraction();
fraction operator+(const fraction &f2) const;
fraction operator-(const fraction &f2) const;
fraction operator*(const fraction &f2) const;
fraction operator/(const fraction &f2) const;
int getfenzi();
int getfenmu();
void result();
friend void convertF(fraction &f);
private:
int fenzi;
int fenmu;
}; #endif

2.fraction.cpp

 #include<iostream>
#include"fraction.h"
using namespace std;
//构造函数
fraction::fraction(int a,int b):fenzi(a),fenmu(b){
}
//fraction::fraction(fraction &f):fenzi(f.fenzi),fenmu(f.fenmu){
//}为啥这里用复制构造函数反而使函数报错 // 析构函数
fraction::~fraction(){
}
fraction fraction::operator+(const fraction &f2) const{
if(fenmu==f2.fenmu)
{
return fraction(fenzi+f2.fenzi,fenmu);
}
else{
return fraction(fenzi*f2.fenmu+fenmu*f2.fenzi,fenmu*f2.fenmu);
}
}
//运算符重载
fraction fraction::operator-(const fraction &f2) const{
if(fenmu==f2.fenmu)
{
return fraction(fenzi-f2.fenzi,fenmu);
}
else{
return fraction(fenzi*f2.fenmu-fenmu*f2.fenzi,fenmu*f2.fenmu);
}
}
fraction fraction::operator*(const fraction &f2) const{
return fraction(fenzi*f2.fenzi,fenmu*f2.fenmu);
}
fraction fraction::operator/(const fraction &f2) const{
return fraction(fenzi*f2.fenmu,fenmu*f2.fenzi);
}
//访问私有成员
int fraction::getfenmu(){
return fenmu;
} int fraction::getfenzi(){
return fenzi;
}
//输出最后结果
void fraction::result(){
cout<<fenzi<<"/"<<fenmu<<endl;
}
//友元函数规范化
//第一次出错因为在实现函数时也加进了友元标识
void convertF(fraction &f){ int a,b,t;
a=f.getfenzi();
b= f.getfenmu();
if(a>=b){
t=a/b;
while(a>b){
a=a-b;
}
cout<<"分数应该化为:"<<t<<"+"<<a<<"/"<<b<<endl;
}
else cout<<"分数就是:"<<a<<"/"<<b<<endl; }

3.ifraction.h

 #ifndef ifraction_h
#define ifraction_h
#include"fraction.h"
class ifraction:public fraction {
public:
ifraction(int a=,int b=);
void printfra();
~ifraction();
friend void convertF(ifraction &f);
}; #endif

4.ifraction.cpp

 #include"ifraction.h"
#include<iostream>
using namespace std; void ifraction::printfra(){
cout<<getfenzi()<<"/"<<getfenmu()<<endl;
} ifraction::ifraction(int a,int b):fraction(a,b){
} ifraction::~ifraction(){
} void convertF(ifraction &f){ int a,b,t;
a=f.getfenzi();
b= f.getfenmu();
if(a>=b){
t=a/b;
while(a>b){
a=a-b;
} cout<<"分数应该化为:"<<t<<"+"<<a<<"/"<<b<<endl;
}
else cout<<"分数就是:"<<a<<"/"<<b<<endl; }

5.main.cpp

 #include<iostream>
using namespace std;
#include"fraction.h"
#include"ifraction.h" int main(){
ifraction a(,),b(,),c(,);
//c=a+b;//测试了运算符重载,发现这里报错,为什么?是运算符重载不能继承吗?
//检查之后发现是虽然能重载,返回值的类型却是fraction类类型,比如一个函数原本是int 类型,继承之后也不会变成double吧 fraction d,e(,); d=a+b;
cout<<"输出a+b=";
d.result();
cout<<"输出a-b=";
d=a-b;
d.result();
cout<<"输出a*b=";
d=a*b;
d.result();
cout<<"输出a/b=";
d=a/b;
d.result();
cout<<"输出ifraction的对象c:";
c.printfra();
convertF(e);
convertF(c);
return ;
}

运行截图:

该实验总结:

运算符重载能不能被继承?修改过后的代码显示当然可以。是不是所有的运算符重载都能被继承?

查到赋值操作符的特殊,如下解释:

class widget
{
① widget& operator=( const widget& rhs ){} // 这个叫做赋值操作符
② widget& operator=( const int ) {} // 这个叫做赋值操作符重载
} ; ①. 赋值操作符属于类的复制控制的一部分(默构,复构,赋值,析构), 自己不定义,编译器会自动合成.它的正式叫法是(copy assignment operator),强调的是属于复制控制的一部分. ②. 赋值操作符重载和赋值操作符不一样,你不定义,编译器不会自动合成. 所以你要是问子类赋值操作符会不会继承父类,那肯定是不会的.
1. 如果 子类没定义赋值操作符, 那么 子类会自动合成赋值操作符, 子类在赋值的时候会自动调用父类的赋值操作符来完成基类部分的复制拷贝.
2. 如果 子类自己定义了赋值操作符, 那么 子类就不会继续自动合成, 仍然子类必须手动调用父类的赋值操作符来完成基类部分的赋值拷贝,否则会造成部分复制( partial copy assignment )

4. (***选做***) 基于提供的程序文件,补足并扩充程序,实现一个多类型玩家角色扮演游戏。 在本次实验附件包 ex4 中有如下文件: container.h, container.cpp, player.h, player.cpp, swordsman.h, swordsman.cpp, main.cpp (1)阅读源码,理解并补足程序,让程序运行生效。 其中,程序中出现有????????之处,是需要补足的部分。 (2)画出这个角色扮演游戏 UML 类图,尤其是类和类之间的关系 (3)设计并实现 archer 类和 mage 类。在 UML 类图中也加进这两个新类。 (4)修改 main 函数,随机生成不同角色的敌人,并保证程序正常运行。 (5)为游戏增加其它元素,完善游戏的可玩性、趣味性,等。 (说明:这道涉及虚函数、运行时多态。你可以在第 8 章学完后尝试编写,或者, 在尝试编写这道题的过程中,学习第 8 章虚函数和运行时多态的知识。 )

这道题待我计算完毕之后再行更新。。。

【C++ 实验六 继承与派生】的更多相关文章

  1. c++学习--继承与派生

    继承和派生 1 含有对象成员(子对象)的派生类的构造函数,定义派生类对象成员时,构造函数的执行顺序如下: 1 调用基类的构造函数,对基类数据成员初始化: 2 调用对象成员的构造函数,对对象成员的数据成 ...

  2. C++复习:继承与派生

    1继承概念 面向对象程序设计有4个主要特点:抽象.封装.继承和多态性.说了类和对象,了解了面向对象程序设计的两个重要特征一数据抽象与封装,已经能够设计出基于对象的程序,这是面向对象程序设计的基础. 要 ...

  3. 实验 六:分析linux内核创建一个新进程的过程

    实验六:分析Linux内核创建一个新进程的过程 作者:王朝宪  <Linux内核分析>MOOC课程http://mooc.study.163.com/course/USTC-1000029 ...

  4. java 实验3 继承+多态

    实验3  继承与多态 **类可以实现多个接口 但只有单继承!** 1.继承 1).继承语法  class 子类名 extends 父类{    } 2).构造函数(通过source即可得到) 注意: ...

  5. Day08:继承与派生,多态,封装,绑定与非绑定方法,面向对象高级(反射,__str__,__del__)

    上节课复习:1.编程思想    面向过程        核心是过程二字,过程指的是解决问题的步骤,即先干什么再干什么后干什么        基于该思想编写程序就好比在设计一条流水线,是一种机械式的思维 ...

  6. Python面向对象编程——继承与派生

    Python面向对象编程--继承与派生 一.初始继承 1.什么是继承 继承指的是类与类之间的关系,是一种什么"是"什么的关系,继承的功能之一就是用来解决代码重用问题. 继承是一种创 ...

  7. 类属性与对象实现,init方法的作用,绑定方法,绑定方法与普通函数的区别,继承,抽象与继承,派生与覆盖

    今日内容: 1.类属性与对象属性 2.init方法的作用 3.绑定方法 4.绑定方法与普通函数的区别(非绑定方法) 5.继承 6.抽象与继承 7.派生与覆盖 1.类属性与对象属性 类中应该进存储所有对 ...

  8. 不可或缺 Windows Native (21) - C++: 继承, 组合, 派生类的构造函数和析构函数, 基类与派生类的转换, 子对象的实例化, 基类成员的隐藏(派生类成员覆盖基类成员)

    [源码下载] 不可或缺 Windows Native (21) - C++: 继承, 组合, 派生类的构造函数和析构函数, 基类与派生类的转换, 子对象的实例化, 基类成员的隐藏(派生类成员覆盖基类成 ...

  9. [C++]类的继承与派生

    继承性是面向对象程序设计的第二大特性,它允许在既有类的基础上创建新类,新类可以继承既有类的数据成员和成员函数,可以添加自己特有的数据成员和成员函数,还可以对既有类中的成员函数重新定义.利用类的继承和派 ...

随机推荐

  1. SSH HTTP代理

    SSH 连接 参照https://stackoverflow.com/questions/19161960/connect-with-ssh-through-a-proxy 若要使用goflyway连 ...

  2. [物理学与PDEs]第1章习题8 磁场分布 $\ra$ 电流分布

    设在真空中有一圆柱形磁场 $$\bex B(P)=\sedd{\ba{ll} \cfrac{2I}{Cr},&r\geq R,\\ \cfrac{2I}{CR^2}r,&r<R, ...

  3. [物理学与PDEs]第1章习题1 无限长直线的电场强度与电势

    设有一均匀分布着电荷的无限长直线, 其上的电荷线密度 (即单位长度上的电荷量) 为 $\sigma$. 试求该直线所形成的电场的电场强度及电势. 解答: 设空间上点 $P$ 到直线的距离为 $r$, ...

  4. python学习02

    python的数据类型 程序=数据类型+算法 1.数据类型:数据型,字符串,列表list,字典dict,set集合(),tuple元组() 1)数据型 int,整数型,理论上是无限大,不过受到机器内存 ...

  5. KL散度

    摘自: https://www.jianshu.com/p/43318a3dc715?from=timeline&isappinstalled=0 一.解决的问题 量化两种概率分布P和Q可以使 ...

  6. nnet3 TDNN chunk, left-context, right-context

    chunk-width 数据块的宽度 NnetIo name=="input" indexes,left-context+num-frame+right-context=5+7+6 ...

  7. jenkins备份与恢复【转】

    jenkins这里我通过thinbackup插件进行对jenkins的配置备份与恢复 1丶安装thinbackup插件 2丶系统管理选择thinbackup插件 3丶创建备份目录 mkdir /bac ...

  8. Copley-STM32串口+CANopen实现双电机力矩同步

    原来有个CANopen的主站卡,现在没了,只有单片机,用单片机来制作一个CANopen的主站卡貌似不是很难,但是需要时间.无奈仔细看了一个Copley的说明,决定采用CAN口+串口来实现之前的功能. ...

  9. flex使内部内容自适应宽度

  10. iOS -- Effective Objective-C 阅读笔记 (4)

    1: 在 对象内部 尽量 直接访问 实例变量 在对象之外访问实例变量时, 总是应该通过属性来访问, 然而在对象内部, 在读取实例变量的时候尽量采用 直接访问的形式, 而在设置实例变量的时候通过属性来做 ...