C++第三次实验.docx
《C++第三次实验.docx》由会员分享,可在线阅读,更多相关《C++第三次实验.docx(18页珍藏版)》请在冰豆网上搜索。
![C++第三次实验.docx](https://file1.bdocx.com/fileroot1/2023-8/15/69a30c91-900e-477e-b481-fb4f54ad9bd7/69a30c91-900e-477e-b481-fb4f54ad9bd71.gif)
C++第三次实验
天津理工大学
计算机与通信工程学院
实验报告
2013至2014学年第二学期
课程名称
高级语言程序设计Ⅱ
实验(3)
实验名称
派生与继承
实验时间
2013年4月21日第3节至第6节
学号姓名
专业
信息安全
主讲教师
唐召东
辅导教师
唐召东
软件环境
VC++6
硬件环境
PC机
实验目的
(1)理解继承的含义,掌握派生类的定义方法和实现;
(2)理解公有继承下基类成员对派生类成员和派生类对象的可见性,能正确地访问继承层次中的各种类成员;
(3)理解保护成员在继承中的作用,能够在适当的时候选择使用保护成员以便派生类成员可以访问基类的部分非公开的成员;
(4)理解虚函数在类的继承层次中的作用,虚函数的引入对程序运行时的影响,能够对使用虚函数的简单程序写出程序结果。
实验内容(应包括实验题目、实验要求、实验任务等)
二、练习项目:
1.先定义“点”类Point,再由“点”类派生出“圆”类Circle。
#include
#definePI3.14159
classPoint//定义“点”类
{
intx,y;
public:
Point(inta=0,intb=0)
{
x=a;y=b;
}
voidShowPoint()
{
cout<<"Point:
("<}
intGetx()
{
returnx;
}
intGety()
{
returny;
}
voidSetxy(inta,intb)
{
x=a;y=b;}
};
classCircle:
publicPoint//定义“圆”类,公有继承
{
intr;//“圆”的半径
public:
Circle(intx,inty,intra):
Point(x,y)//B
{r=ra;}
voidSetr(intra)
{r=ra;}
doubleArea()//求圆的面积
{returnPI*r*r;}
voidMove(intx_offset,inty_offset)//将圆心坐标平移
{
intx1=Getx();//存取基类的私有成员
inty1=Gety();//D
x1+=x_offset;y1+=y_offset;
Setxy(x1,y1);//E
}
voidShowCircle()
{
ShowPoint();//F
cout<<"Radius:
"<cout<<"Area:
"<
}
};
voidmain()
{
Circlec(1,1,1);
c.ShowCircle();
c.Move(1,2);
c.ShowCircle();
c.Setxy(4,5);//重新置圆心坐标
c.Setr
(2);//重新置半径值
c.ShowCircle();
}
(1)记录程序的运行结果。
(2)测试能否将move函数体改写为
x=x+x_offset;
y=y+y_offset;
2.先定义“点”类Point和“半径”类Radius,再由Point类和Radius类多重派生出“圆”类Circle。
#include
#definePI3.14159
classPoint
{
protected:
//A
intx,y;
public:
Point(inta=0,intb=0){x=a;y=b;}
voidShowPoint()
{cout<<"Point:
("<intGetx(){returnx;}
intGety(){returny;}
voidSetxy(inta,intb){x=a;y=b;}
};
classRadius
{
protected:
//B
intr;
public:
Radius(intra=0){r=ra;}
voidSetr(intra){r=ra;}
intGetr(){returnr;}
};
classCircle:
publicPoint,publicRadius
{
public:
Circle(intx,inty,intra):
Point(x,y),Radius(ra)//D
{}
doubleArea()
doubleArea()
{returnPI*r*r;}//直接访问基类的保护成员
voidMove(intx_offset,inty_offset)
{x+=x_offset;y+=y_offset;}
voidShowCircle()
{
ShowPoint();
cout<<"Radius:
"<cout<<"Area:
"<
}
};
voidmain()
{
Circlec(1,1,1);
c.ShowCircle();
c.Move(1,2);
c.ShowCircle();
c.Setxy(4,5);
c.Setr
(2);
c.ShowCircle();
}
(1)记录程序的运行结果
(2)为什么可以直接使用x,y
(3)如果x,y在基类中是私有的行吗?
3.多重继承中基类构造函数和析构函数的调用顺序
#include
classBase1
{
protected:
intdata1;
public:
Base1(inta=0)
{data1=a;}
cout<<"BaseConstructor1\n";
}
~Base1()
{cout<<"BaseDestructor1\n";}
};
classBase2
{
protected:
intdata2;
public:
Base2(inta=0)
{data2=a;
cout<<"BaseConstructor2\n";
}
~Base2()
{cout<<"BaseDestructor2\n";}
};
classDerived:
publicBase1,publicBase2
{
intd;
public:
Derived(intx,inty,intz):
Base1(x),Base2(y)
{d=z;cout<<"DerivedConstructor\n";}
~Derived()
{cout<<"DerivedDestructor\n";}
voidShow()
{cout<};
voidmain()
{Derivedc(1,2,3);
c.Show();
}
(1)记录程序的运行结果
4.对象成员构造函数和析构函数的调用顺序
#include
classBase1
{
protected:
intdata1;
public:
Base1(inta=8)
{data1=a;
cout<}
~Base1()
{cout<};
classBase2
{
protected:
intdata2;
public:
Base2(inta=9)
{data2=a;
cout<}
~Base2()
{cout<};
classDerived:
publicBase1,publicBase2
{intd;
Base1b1,b2;
public:
Derived(intx,inty,intz):
Base1(x),Base2(y),b1(x+y),b2(x+z)
{d=z;cout<<"DerivedConstructor\n";}
~Derived()
{cout<<"DerivedDestructor\n";}
voidShow()
{cout<};
voidmain()
{Derivedc(1,2,3);
c.Show();
}
(1)记录程序的运行结果
5.编程题
假设某商店有如下几种货品:
衬衣、帽子、立柜。
每一种货物都有与其关联的说明信息。
衬衣:
单价、产地、库存量、布料;
帽子:
单价、产地、库存量、布料、样式(平顶或尖顶);
立柜:
单价、产地、库存量、木料、颜色。
对这些商品的操作有:
商品的进库(增加库存量),商品的出库(减少库存量),该类货
品总价格的计算。
要求自行设计数据结构,用类的继承与派生关系将上述的各种货品表示出来,并使用类
的构造函数来初始化每一类对象的初始数据。
而后将上述的商品管理计算机化,完成操作要
求的功能。
【实现方法提示】
1.设立3个不同的类来描述与处理3种不同的货品。
首先注意到上述3种货品数据之
间的相互关联关系,可使用C++基类及其派生类的定义方法,先抽象出(“提取”出)如下每
一货品都具有的“公有”数据构成一个所谓的基类base,而后再派生出所需的那3个类。
(1)base(基)类:
单价、产地、库存量;
(2)由base作为基类,派生出shirt(衬衣)类:
增加“布料”数据;
(3)由base出发,派生出wardrobe(立柜)类:
增加“木料”与“颜色”数据;
(4)而后又由shirt类出发(作为基类),派生出cap(帽子)类:
增加“样式”数据。
2.对应于要对各类数据所进行的操作,而设立出类的如下几个成员函数。
(1)构造函数
通过传递来的实参数据,来构造出每一对象所具有的各数据成员。
如基类base需要传
递place、count与price三项数据,而派生类shirt则需在base数据的基础上增加第四项
即布料数据material等。
(2)商品的进库(增加库存量)
voidin_something(intadd_cnt);
将对象的库存量count增加一个数量add_cnt。
(3)商品的出库(减少库存量)
voidout_something(intdel_cnt);
将对象的库存量count减少一个数量del_cnt。
(4)该类货品总价格的计算
doubletotal_price();
通过使用“price*count”计算并返回对象所代表货品的总价格。
(5)对象数据的输出。
在屏幕上显示出对象所拥有的当前数据。
实验过程与实验结果(可包括实验实施的步骤、算法描述、流程、结论等)
1.源代码:
见实验内容中的源代码。
输出结果:
测试能否将move函数体改写为
x=x+x_offset;
y=y+y_offset;
答:
不能
2.源代码:
见实验内容中的源代码。
输出结果:
为什么可以直接使用x,y?
答:
x,y为保护继承,可以被派生类使用
如果x,y在基类中是私有的行吗?
答:
不行
3.源代码:
见实验内容中的源代码。
输出结果:
4.源代码:
见实验内容中的源代码。
输出结果:
5.源代码:
count”计算并返回对象所代表货品的总价格。
(5)对象数据的输出。
在屏幕上显示出对象所拥有的当前数据。
源代码如下:
#include
#include
usingnamespacestd;
classBase
{
private:
doubleprice;
stringplace;
intcount;
public:
Base(double_price=0.0,string_place="NULL",int_count=0)
{
price=_price;
place=_place;
count=_count;
}
virtual~Base(){};
voidadd(intx)
{
count-=x;
}
doubletotal()
{
returncount*price;
}
doublegetprice()
{
returnprice;
}
stringgetplace()
{
returnplace;
}
intgetcount()
{
returncount;
}
voidsetprice(double_price=0.0)
{
price=_price;
}
voidsetplace(string_place="NULL")
{
place=_place;
}
voidsetcount(int_count)
{
count=_count;
}
voidprint()
{
cout<<"单价:
"<"<"<"<}
};
classShirt:
publicBase
{
private:
stringmateral;
public:
Shirt(double_price=0.0,string_place="NULL",int_count=0,string_materal="NULL"):
Base(_price,_place,_count)
{
materal=_materal;
}
virtual~Shirt(){};
voidsetmateral(string_materal)
{
materal=_materal;
}
stringgetmateral()
{
returnmateral;
}
voidprint()
{
Base:
:
print();
cout<<"布料:
"<}
};
classWardrobe:
publicBase
{
private:
stringmateral;
stringcolor;
public:
Wardrobe(double_price=0.0,string_place="NULL",int_count=0,string_materal="NULL",string_color="NULL"):
Base(_price,_place,_count)
{
materal=_materal;
color=_color;
}
~Wardrobe(){}
voidsetmateral(string_materal)
{
materal=_materal;
}
stringgetmateral()
{
returnmateral;
}
voidsetcolor(string_color)
{
color=_color;
}
stringgetcolor()
{
returncolor;
}
voidprint()
{
Base:
:
print();
cout<<"木料:
"<"<}
};
classCap:
publicShirt
{
private:
stringstyle;
public:
Cap(double_price=0.0,string_place="NULL",int_count=0,string_materal="NULL",string_style="NULL"):
Shirt(_price,_place,_count,_materal)
{
style=_style;
}
~Cap(){}
voidsetstyle(string_style)
{
style=_style;
}
stringgetstyle()
{
returnstyle;
}
voidprint()
{
Shirt:
:
print();
cout<<"样式:
"<