Ex8_5_2.cpp
上传用户:wuzhousb
上传日期:2022-07-12
资源大小:380k
文件大小:6k
源码类别:

书籍源码

开发平台:

Visual C++

  1. //【例8.5_2】赋值兼容规则与自定义的拷贝构造函数。采用动态建立的C风格字符串,深拷贝。
  2. #include<iostream>
  3. #include<cstring>
  4. using namespace std;
  5. enum Tsex{mid,man,woman};
  6. struct course{
  7. char* coursename;
  8. int grade;
  9. };
  10. class Person{
  11. char IdPerson[19]; //身份证号,18位数字
  12. char *Name; //姓名
  13. Tsex Sex; //性别
  14. int Birthday; //生日,格式1986年8月18日写作19860818
  15. char *HomeAddress; //家庭地址
  16. public:
  17. Person(char *,char *,Tsex,int,char *);
  18. Person();
  19. Person(Person &ps);
  20. ~Person();
  21. Person & operator=(const Person &);
  22. void PrintPersonInfo();
  23. };
  24. Person::Person(char *id,char *name,Tsex sex,int birthday,char *homeadd){
  25. strcpy(IdPerson,id);
  26. Name=new char[strlen(name)+1];
  27. strcpy(Name,name);
  28. Sex=sex;
  29. Birthday=birthday;
  30. HomeAddress=new char[strlen(homeadd)+1];
  31. strcpy(HomeAddress,homeadd);
  32. }
  33. Person::Person(){
  34. IdPerson[0]='';Name=NULL;Sex=mid;
  35. Birthday=0;HomeAddress=NULL;
  36. }
  37. Person::Person(Person &ps){
  38. strcpy(IdPerson,ps.IdPerson);
  39. if(ps.Name!=NULL){
  40. Name=new char[strlen(ps.Name)+1];
  41. strcpy(Name,ps.Name);
  42. }
  43. else Name=NULL;
  44. Sex=ps.Sex;
  45. Birthday=ps.Birthday;
  46. if(ps.HomeAddress!=NULL){
  47. HomeAddress=new char[strlen(ps.HomeAddress)+1];
  48. strcpy(HomeAddress,ps.HomeAddress);
  49. }
  50. else HomeAddress=NULL;
  51. }
  52. Person::~Person(){
  53. if(Name)delete[]Name;if(HomeAddress) delete [] HomeAddress;
  54. }
  55. Person & Person::operator=(const Person &ps){
  56. strcpy(IdPerson,ps.IdPerson);
  57. if(ps.Name!=NULL){
  58. delete[]Name;//赋值要先清原来分配的空间
  59. Name=new char[strlen(ps.Name)+1];
  60. strcpy(Name,ps.Name);
  61. }
  62. else Name=NULL;
  63. Sex=ps.Sex;
  64. Birthday=ps.Birthday;
  65. if(ps.HomeAddress!=NULL){
  66. delete [] HomeAddress;//赋值要先清原来分配的空间,再重新分配
  67. HomeAddress=new char[strlen(ps.HomeAddress)+1];
  68. strcpy(HomeAddress,ps.HomeAddress);
  69. }
  70. else {
  71. delete [] HomeAddress;
  72. HomeAddress=NULL;
  73. }
  74. return *this;
  75. }
  76. void Person::PrintPersonInfo(){
  77. int i;
  78. cout<<"身份证号:"<<IdPerson<<'n'<<"姓名:"<<Name<<'n'<<"性别:";
  79. if(Sex==man)cout<<"男"<<'n';
  80. else if(Sex==woman)cout<<"女"<<'n';
  81.      else cout<<" "<<'n';
  82. cout<<"出生年月日:";
  83. i=Birthday;
  84. cout<<i/10000<<"年";
  85. i=i%10000;
  86. cout<<i/100<<"月"<<i%100<<"日"<<'n'<<"家庭住址:"<<HomeAddress<<'n';
  87. }
  88. class Student:public Person{//定义派生的学生类
  89. char NoStudent[10];//学号
  90. course cs[30];//30门课程与成绩
  91. public:
  92. Student(char*id,char*name,Tsex sex,int birthday,char*homeadd,char*nostud);
  93. //注意派生类构造函数声明方式
  94. Student();
  95. Student(Student &Std);
  96. ~Student();
  97. Student & operator=(const Student &Std);
  98. SetCourse(char *,int);
  99. int GetCourse(char *);
  100. void PrintStudentInfo();
  101. };
  102. Student::Student(char*id,char*name,Tsex sex,int birthday,char*homeadd,char*nostud)
  103.              :Person(id,name,sex,birthday,homeadd){//注意Person参数表不用类型
  104. int i;
  105. strcpy(NoStudent,nostud);
  106. for(i=0;i<30;i++){//课程与成绩清空
  107. cs[i].coursename=NULL;
  108. cs[i].grade=0;
  109. }
  110. }
  111. Student::Student(){//基类缺省的无参数构造函数不必显式给出
  112. int i;
  113. NoStudent[10]=NULL;
  114. for(i=0;i<30;i++){//课程与成绩清零,将来由键盘输入 
  115. cs[i].coursename=NULL;
  116. cs[i].grade=0;
  117. }
  118. }
  119. Student::Student(Student &Std):Person(Std){//按赋值兼容规则Std可为Person实参
  120. int i;
  121. strcpy(NoStudent,Std.NoStudent);
  122. for(i=0;i<30;i++){
  123. if(Std.cs[i].coursename!=NULL){
  124. cs[i].coursename=new char[strlen(Std.cs[i].coursename)+1];
  125. strcpy(cs[i].coursename,Std.cs[i].coursename);
  126. }
  127. else cs[i].coursename=NULL;
  128. cs[i].grade=Std.cs[i].grade;
  129. }
  130. }
  131. Student::~Student(){//基类析构函数不必显式给出
  132. int i;
  133. for(i=0;i<30;i++)
  134. if(cs[i].coursename)delete [] cs[i].coursename;
  135. }//清除各课程名称不可少,它们放在堆区中
  136. Student & Student::operator=(const Student &Std){
  137. int i;
  138. this->Person::operator=(Std);
  139. strcpy(NoStudent,Std.NoStudent);
  140. for(i=0;i<30;i++){
  141. if(Std.cs[i].coursename!=NULL){
  142. delete [] cs[i].coursename;//拷贝要先清原来分配空间,再重新分配
  143. cs[i].coursename=new char[strlen(Std.cs[i].coursename)+1];
  144. strcpy(cs[i].coursename,Std.cs[i].coursename);
  145. }
  146. else cs[i].coursename=NULL;
  147. cs[i].grade=Std.cs[i].grade;
  148. }
  149. return *this;
  150. }
  151. int Student::SetCourse(char *coursename,int grade){
  152. int i;
  153. bool b=false;//标识新输入的课程,还是更新成绩
  154. for(i=0;i<30;i++){
  155. if(cs[i].coursename==NULL){
  156. //判表是否进入未使用部分(如有对应删除应按顺序表方式)
  157. cs[i].coursename=new char[strlen(coursename)+1];
  158. strcpy(cs[i].coursename,coursename);
  159. cs[i].grade=grade;
  160. b=false;
  161. break;
  162. }
  163. else if(!strcmp(cs[i].coursename,coursename)){
  164. //后查是否已有该课程记录。如先查,因strcmp()健壮型不好,遇NULL出错
  165. cs[i].grade=grade;
  166. b=true;
  167. break;
  168. }
  169. }
  170. if(i==30) return 0;//成绩表满返回0
  171. if(b) return 1;//修改成绩返回1
  172. else return 2;//登记成绩返回2
  173. }
  174. int Student::GetCourse(char *coursename){
  175. int i;
  176. for(i=0;i<30;i++)
  177. if(cs[i].coursename==NULL) break;//无此句,stcpy()会出错
  178. else if(!strcmp(cs[i].coursename,coursename))return cs[i].grade;
  179. return -1;
  180. }//找到返回成绩,未找到返回-1
  181. void Student::PrintStudentInfo(){
  182. int i;
  183. cout<<"学号:"<<NoStudent<<'n';
  184. PrintPersonInfo();
  185. for(i=0;i<30;i++)//打印各科成绩
  186. if(cs[i].coursename!=NULL)cout<<cs[i].coursename<<'t'<<cs[i].grade<<'n';
  187. else break;
  188. cout<<"--------完-------- "<<endl;
  189. }
  190. int main(void){
  191. char temp[30];
  192. int i,k;
  193. Person per1("320102820818161","沈俊",man,19820818,"南京四牌楼2号");
  194. per1.PrintPersonInfo();
  195. Person per2=per1,per3;//基类对象拷贝初始化,深拷贝
  196. per2.PrintPersonInfo();
  197. per3=per1;//基类对象深拷贝
  198. per3.PrintPersonInfo();
  199. Student stu1("320102811226161","朱海鹏",man,19811226,"南京市黄浦路1号","06000123");
  200. cout<<"请输入各科成绩:"<<'n';//为简单仅以一个学生为例。完整应输入学号,查找,再操作
  201. while(1){//输入各科成绩,输入"end"停止
  202. cin>>temp;//输入格式:物理  80
  203. if(!strcmp(temp,"end")) break;
  204. cin>>k;
  205. i=stu1.SetCourse(temp,k);
  206. if(i==0)cout<<"成绩列表已满!"<<'n';
  207. else if(i==1)cout<<"修改成绩"<<'n';
  208.      else cout<<"登记成绩"<<'n';
  209.     }
  210. stu1.PrintStudentInfo();
  211. while(1){
  212. cout<<"查询成绩"<<'n'<<"请输入科目:"<<'n';
  213. cin>>temp;
  214. if(!strcmp(temp,"end")) break;
  215. k=stu1.GetCourse(temp);
  216. if(k==-1)cout<<"未查到"<<'n';
  217. else cout<<k<<'n';
  218. }
  219. Student stu2=stu1,stu3;//派生类对象深拷贝初始化
  220. stu2.PrintStudentInfo();
  221. stu3=stu2;//派生类对象深拷贝
  222. stu3.PrintStudentInfo();
  223. return 0;
  224. }