![img](file:///C:\Users\86176\AppData\Local\Temp\ksohtml60740\wps1.png)![img](file:///C:\Users\86176\AppData\Local\Temp\ksohtml60740\wps2.jpg)面向对象程序设计 石家庄铁道大学信息学院
实验6:多态****—虚函数
本次实验属于模仿型实验,通过本次实验学生将掌握以下内容:
1、掌握虚函数的使用方法
2、理解虚函数的使用在程序中带来的便捷
![img](file:///C:\Users\86176\AppData\Local\Temp\ksohtml60740\wps3.png)
[实验任务二]:****人、学生和教师
设计一个类people,有保护数据成员:age(年龄,整型),name(姓名,string),行为成员:两个构造函数(一个默认,另一个有参数);默认析构函数;void setValue(int m, string str)给age和name赋值;有一个void类型的纯虚函数display()。
设计一个学生类student,公有继承类people,有私有成员:studentID(学号,整型),行为成员:两个构造函数(一个默认,另一个有参数);默认析构函数;void setID(int m)给studentID赋值;display()函数输出学生的姓名,年龄,学号。
设计一个教师类teacher,公有继承类people,有私有成员:teacherID(工号,整型),行为成员:两个构造函数(一个默认,另一个有参数);默认析构函数;void setID(int m)给teacherID赋值; display()函数输出教师的姓名,年龄,工号。
在main函数定义学生对象和教师对象,利用父类指针给对象初始化赋值或调用setValue()和setID()赋值,并输出学生和老师的信息。
提示:纯虚函数所在类不可定义对象
实验要求:
1.注意加上必要的输入输出提示;
2.注意开头的标注部分,加上自己的姓名以及修改日期;
#include<iostream>
using namespace std;
class People
{
protected:
int age;
string name;
public:
People(){}
People(int a,string n):age(a),name(n){}
~People(){}
void setvalue(int m, string str)
{
age = m;
name = str;
}
virtual void display()
{
cout << "姓名为:" << name << " " << "年龄为:" << age << endl;
}
};
class student :public People
{
private:
int stuid;
public:
student(){}
student(int a,string n,int i):People(a,n),stuid(i){}
~student(){}
void setid(int m)
{
stuid = m;
}
void display()
{
cout<<"学号为:"<<stuid<<" " << "姓名为:" << name << " " << "年龄为:" << age << endl;
}
};
class teacher :public People
{
private:
int teaid;
public:
teacher() {}
teacher(int a, string n, int i) :People(a, n), teaid(i) {}
~teacher() {}
void setid(int m)
{
teaid = m;
}
void display()
{
cout << "工号为:" << teaid << " " << "姓名为:" << name << " " << "年龄为:" << age << endl;
}
};
void m(People& p)
{
p.display();
}
int main()
{
student s(18, "郭永刚", 20223964);
m(s);
teacher t(39, "迪迦", 369852);
m(t);
}
[实验任务三]:****动物类
【问题描述】
定义猫科动物Animal类,由其派生出猫类(Cat)和豹类(Leopard),在Animal类中定义虚函数,输出“My name is Animal”,在派生类中分别重新定义该函数,显示“My name is ”,其中为各自类名
【输入形式】
无输入内容
【输出形式】
三个类的speak函数输出
【样例输入】
无
【样例输出】
My name is Animal.
My name is Cat.
My name is Leopard.
【样例说明】
输出形式中每句话后为英文句号”.”
My name is Animal.
My name is Cat.
My name is Leopard.
请按任意键继续. . .
实验要求:
\1. 每个类都有各自的构造函数(2个)和析构函数;
\2. 在主函数中分别定义三个类的对象和基类指针,通过指针完成对子类speak函数的调用。
\3. 思考:若要求在基类中将speak声明为纯虚函数,程序该如何修改?是否还能定义Animal类的对象?
#include<iostream>
using namespace std;
class Animal
{
public:
virtual void speak()
{
cout << "My name is Animal" << endl;
}
};
class Leopard :public Animal
{
public:
void speak()
{
cout << "My name is leopard" << endl;
}
};
class Cat :public Animal
{
public:
void speak()
{
cout << "My name is Cat" << endl;
}
};
void s(Animal* a)
{
a->speak();
}
int main()
{
Cat c;
Leopard l;
s(&c);
s(&l);
return 0;
}
[实验任务四]:形状类
【问题描述】
定义shape类,无数据成员,包含两个纯虚函数成员void setvalues() 和float area() ,由shape类进行派生如下:
矩形类,包含两个数据成员变量用于描述底和高,均为float类型,重新定义上述两个纯虚函数成员,完成数据成员值的设定和面积的计算;
三角形类,包含两个数据成员变量用于描述底和高,均为float类型,重新定义上述两个纯虚函数成员,完成数据成员值的设定和面积的计算;
正方形类,包含一个数据成员变量用于描述边长,float类型,重新定义上述两个纯虚函数成员,完成数据成员值的设定和面积的计算;
圆形类,包含一个数据成员变量用于描述半径,float类型,重新定义上述两个纯虚函数成员,完成数据成员值的设定和面积的计算;
在主函数中定义相应的指针对象和普通对象,利用虚函数实现多态,依次分别输入矩形的底和高,三角形的底和高,正方形的边长,圆形的半径,若其中任何一个值小于等于0,则输出Set Value Error!,然后退出程序,对于之前已正确输入的数值计算相应形状的面积。
【输入形式】
矩形的底和高
三角形的底和高
正方形的边长
圆形的半径
【输出形式】
矩形面积
三角形面积
正方形面积
圆形面积
【输入样例1】
4 5 4 5 5 1
【输出样例1】
20
10
25
3.1415
【输入样例2】
1.2 6.5 9 -6 3 2
【输出样例2】
7.8
Set Value Error!
【样例说明】
计算圆面积的圆周率取值为3.1415
测试数据
4 5 4 5 5 1
20
10
25
3.1415
请按任意键继续. . .
1.5 2.3 4 6.5 9.1 5.2
3.45
13
82.81
84.9462
请按任意键继续. . .
1.3 6.9 7.8 6.3 4.2 5.1
8.97
24.57
17.64
81.7104
请按任意键继续. . .
1.2 6.5 9 -6 3 2
7.8
Set Value Error!
请按任意键继续. . .
1.2 6.5 3.1 2.4 9.8 -7.6
7.8
3.72
96.04
Set Value Error!
请按任意键继续. . .
实验要求:
1.注意加上必要的输入输出提示;
2.注意开头的标注部分,加上自己的姓名以及修改日期;
#include<iostream>
using namespace std;
#define PI 3.1415
class shape
{
public:
virtual void setvalue() = 0;
virtual float area() = 0;
};
class ju :public shape
{
private:
float s, h;
public:
void setvalue()
{
cin >> s >> h;
if (s < 0 || h < 0)
{
cout << "Set Value Error!" << endl;
exit(0);
}
}
float area()
{
return s * h;
}
};
class san :public shape
{
private:
float s, h;
public:
void setvalue()
{
cin >> s >> h;
if (s < 0 || h < 0)
{
cout << "Set Value Error!" << endl;
exit(0);
}
}
float area()
{
return s * h/2;
}
};
class squre :public shape
{
private:
float a;
public:
void setvalue()
{
cin >> a;
if (a < 0)
{
cout << "Set Value Error!" << endl;
exit(0);
}
}
float area()
{
return a*a;
}
};
class yuan :public shape
{
private:
float r;
public:
void setvalue()
{
cin >> r;
if (r < 0)
{
cout << "Set Value Error!" << endl;
exit(0);
}
}
float area()
{
return r*r*PI;
}
};
void dowork(shape & p)
{
p.setvalue();
cout << p.area() << endl;
}
int main()
{
ju j;
san s;
squre a;
yuan y;
dowork(j);
dowork(s);
dowork(a);
dowork(y);
[实验任务五]:学生类
【问题描述】定义描述学生的student类,包含受保护两个数据成员,分辨是描述姓名的,string类型和描述学号的,int类型,构造函数有两个形参,用于设定这两个数据成员的值,此外包含6个成员函数,用于设定姓名和学号的函数,void setnameid(), 用于显示姓名和学号的函数void displaynameid(),以及四个纯虚函数void setmajor() ,string getmajor() , void setadvisor() 和 string getadvisor();
由学生类派生本科生类understud,新增受保护数据成员,描述专业,string类型,构造函数具有三个形参,重新定义函数void setmajor() 和string getmajor(),用于设置专业和获取专业;
由本科生类派生研究生类poststud,新增私有数据成员,描述导师姓名,string类型,构造函数具有四个形参,且具有缺省值,学生姓名缺省值为“***”,学号缺省值为-1,专业缺省值为“###”,导师姓名缺省值为“&&&”,重新定义函数void setadvisor() 和 string getadvisor(),用于设置导师属性和获取导师属性值;
在主函数中定义相应的指针对象和普通对象,请问可以定义哪些(哪个)类的普通对象,为什么(在实验报告中回答),定义开关变量,int型,通过输入进行赋值,若该值为0,则输出研究生对象的默认属性值,若非零,则依次输入姓名、学号、专业和导师信息,并依次打印出来。
【输入形式】
0
或
1
姓名、学号、专业和导师信息
【输出形式】
姓名和学号
专业
导师姓名
【输入样例1】
0
【输出样例1】
*** -1
###
&&&
【输入样例2】
1
zhang 123 computer li
【输出样例2】
zhang 123
computer
li
测试数据:
0
*** -1
###
&&&
请按任意键继续. . .
1
zhang 123 computer li
zhang 123
computer
li
请按任意键继续. . .
1
wang 001 civil zhao
wang 1
civil
zhao
请按任意键继续. . .
5
zhou 002 electronic wu
zhou 2
electronic
wu
请按任意键继续. . .
实验要求:
1.注意加上必要的输入输出提示;
2.注意开头的标注部分,加上自己的姓名以及修改日期;
#include<iostream>
using namespace std;
class student
{
protected:
string name;
int id;
public:
student(){}
student(string n,int i):name(n),id(i){}
void setnameid()
{
cin >> name >> id;
}
void displaynameid()
{
cout << "姓名:" << name << " " << "学号:" <<id<< endl;
}
virtual void setmajor() = 0;
virtual string getmajor() = 0;
virtual void setadvisor() = 0;
virtual string getadvisor() = 0;
};
class understud:public student
{
protected:
string subject;
public:
understud(){}
understud(string n,int i,string s):student(n,i),subject(s){}
void setmajor()
{
cin >> subject;
}
string getmajor()
{
return subject;
}
};
class poststu :public understud
{
private:
string advitor;
public:
poststu(string n="***",int i=-1,string s="###",string a="&&&"):understud(n,i,s),advitor(a){}
void setadvisor()
{
cin >> advitor;
}
string getadvisor()
{
return advitor;
}
};
int main()
{
int n;
cin >> n;
if (n == 0)
{
poststu p;
student* s1 = &p;
s1->displaynameid();
cout << s1->getmajor() << endl;
cout << s1->getadvisor() << endl;
}
else
{
poststu p;
student* s1 = &p;
s1->setnameid();
s1->setmajor();
s1->setadvisor();
s1->displaynameid();
cout << s1->getmajor() << endl;
cout<<s1->getadvisor()<<endl;
}
}