C++程序设计(第3版)谭浩强 第11章 习题

1.将例11.1的程序片段补充和改写成一个完整、正确的程序,用公用继承方式。在程序中应包括输入数据的函数,在程序运行时输入num,name,sex,age,addr的值,程序应输出以上5个数据的值。

【解】

//11.1
//1.将例11.1的程序片段补充和改写成一个完整、正确的程序,用公用继承方式。
//  在程序中应包括输入数据的函数,在程序运行时输入num,name,sex,age,addr的值,
//  程序应输出以上5个数据的值。

#include 
using namespace std;
class Student
{
public:
	void get_value()
	{
		cin >> num >> name >> sex;
	}//输入基类的3个私有数据成员的值
	void display()
	{
		cout << "num: " << num << endl;//输出基类的3个私有数据成员的值
		cout << "name: " << name << endl;
		cout << "sex: " << sex << endl;
	}
private:
	int num;
	char name[10];
	char sex;
};
class Student1 : public Student//定义公用派生类Student1
{
public:
	void get_value_1()//函数的作用是输入5个数据成员的值
	{
		get_value();//调用函数, 输入基类的3个私有数据成员的值
		cin >> age >> addr;//输入派生类的两个私有数据成员的值
	}
	void display_1()
	{
		cout << "age: " << age << endl;//输出派生类两个私有数据成员的值
		cout << "address: " << addr << endl;
	}
private:
	int age;
	char addr[30];
};
int main()
{
	Student1 stud1;                		//定义公用派生类Student1的对象stud1
	stud1.get_value_1();               		//输入5个数据
	stud1.display();                    	//输出基类的3个私有数据成员的值
	stud1.display_1();                  	//输出派生类两个私有数据成员的值
	return 0;
}

//10101 Li M 20 Beijing↙
//num : 10101
//name : Li
//sex : M
//age : 20
//address : Beijing

2.将例11.2的程序片段补充和改写成一个完整、正确的程序,用私有继承方式。在程序中应包括输入数据的函数,在程序运行时输入num,name,sex,age,addr的值,程序应输出以上5个数据的值。

【解】

//11.2
//2.将例11.2的程序片段补充和改写成一个完整、正确的程序,用私有继承方式。
//  在程序中应包括输入数据的函数,在程序运行时输入num,name,sex,age,addr的值,
//  程序应输出以上5个数据的值。

#include 
using namespace std;
class Student
{
public:
	void get_value()
	{
		cin >> num >> name >> sex;
	}
	void display()
	{
		cout << "num: " << num << endl;
		cout << "name: " << name << endl;
		cout << "sex: " << sex << endl;
	}
private:
	int num;
	char name[10];
	char sex;
};
class Student1 : private Student     		//定义私有派生类Student1
{
public:
	void get_value_1()
	{
		get_value();
		cin >> age >> addr;
	}
	void display_1()
	{
		display();                     	//调用基类中的公用成员函数
		cout << "age: " << age << endl;      	//引用派生类的私有成员, 正确
		cout << "address: " << addr << endl;
	} 	//引用派生类的私有成员, 正确
private:
	int age;
	char addr[30];
};
int main()
{
	Student1 stud1;
	stud1.get_value_1();
	stud1.display_1();                    	//只须调用一次stud1.display_1( )
	return 0;
}

3.将例11.3的程序修改、补充,写成一个完整、正确的程序,用保护继承方式。在程序中应包括输入数据的函数。

【解】

//11.3
//3.将例11.3的程序修改、补充,写成一个完整、正确的程序,用保护继承方式。
//  在程序中应包括输入数据的函数。

#include 
using namespace std;
class Student                       	//声明基类
{
public:                            	//基类公用成员                
	void get_value();
	void display();
protected:                        		//基类保护成员
	int num;
	char name[10];
	char sex;
};
void Student::get_value()
{
	cin >> num >> name >> sex;
}
void Student::display()
{
	cout << "num: " << num << endl;
	cout << "name: " << name << endl;
	cout << "sex: " << sex << endl;
}
class Student1 : protected Student          	//声明一个保护派生类
{
public:
	void get_value_1();
	void display1();
private:
	int age;
	char addr[30];
};
void Student1::get_value_1()
{
	get_value();
	cin >> age >> addr;
}
void Student1::display1()
{
	cout << "num: " << num << endl;        	//引用基类的保护成员
	cout << "name: " << name << endl;      	//引用基类的保护成员
	cout << "sex: " << sex << endl;        	//引用基类的保护成员
	cout << "age: " << age << endl;        	//引用派生类的私有成员
	cout << "address: " << addr << endl;   		//引用派生类的私有成员
}
int main()
{
	Student1 stud1;                     	//stud1是派生类student1类的对象
	stud1.get_value_1();                	//调用派生类对象stud1的公用成员函数
	stud1.display1();                  	//调用派生类对象stud1的公用成员函数
	return 0;
}

4.修改例11.3的程序,改为用公用继承方式。上机调试程序,使之能正确运行并得到正确的结果。对这两种继承方式作比较分析,考虑在什么情况下二者不能互相代替。

【解】

//11.4
//4.修改例11.3的程序,改为用公用继承方式。上机调试程序,
//  使之能正确运行并得到正确的结果。对这两种继承方式作比较分析,
//  考虑在什么情况下二者不能互相代替。

#include 
using namespace std;
class Student               			//声明基类
{
public:                       		//基类公用成员                
	void get_value();
	void display();
protected:                      		//基类保护成员
	int num;
	char name[10];
	char sex;
};
void Student::get_value()
{
	cin >> num >> name >> sex;
}

void Student::display()
{
	cout << "num: " << num << endl;
	cout << "name: " << name << endl;
	cout << "sex: " << sex << endl;
}
class Student1 : public Student           	//声明一个公用派生类
{
public:
	void get_value_1();
	void display1();
private:
	int age;
	char addr[30];
};
void Student1::get_value_1()
{
	get_value();
	cin >> age >> addr;
}
void Student1::display1()
{
	cout << "num: " << num << endl;        	//引用基类的保护成员, 合法
	cout << "name: " << name << endl;     	//引用基类的保护成员, 合法
	cout << "sex: " << sex << endl;        	//引用基类的保护成员, 合法
	cout << "age: " << age << endl;        	//引用派生类的私有成员, 合法
	cout << "address: " << addr << endl;   		//引用派生类的私有成员, 合法
}
int main()
{
	Student1 stud1;                		//stud1是派生类student1类的对象
	stud1.get_value_1();          			//调用派生类对象stud1的公用成员函数get_value_1
	stud1.display1();            			//调用派生类对象stud1的公用成员函数display1
	return 0;
}

5.有以下程序结构,请分析访问属性。(1) 在main函数中能否用b1.i,b1.j和b1.k引用派生类B对象b1中基类A的成员?

(2) 派生类B中的成员函数能否调用基类A中的成员函数f1和f2?

(3) 派生类B中的成员函数能否引用基类A中的数据成员i,j,k?

(4) 能否在main函数中用c1.i,c1.j,c1.k,c1.m,c1.n,c1.p引用基类A的成员i,j,k,派生类B的成员m,n,以及派生类C的成员p?

(5) 能否在main函数中用c1.f1(),c1.f2(),c1.f3()和c1.f4()调用f1,f2,f3,f4成员函数?

【解】

//11.5
//5.有以下程序结构,请分析访问属性。
//  (1) 在main函数中能否用b1.i,b1.j和b1.k引用派生类B对象b1中基类A的成员?
//  (2)派生类B中的成员函数能否调用基类A中的成员函数f1和f2?
//  (3)派生类B中的成员函数能否引用基类A中的数据成员i,j,k?
//  (4)能否在main函数中用c1.i,c1.j,c1.k,c1.m,c1.n,c1.p引用基类A的成员i,j,k,
//	 派生类B的成员m,n,以及派生类C的成员p?
//  (5)能否在main函数中用c1.f1(),c1.f2(),c1.f3()和c1.f4()调用f1,f2,f3,f4成员函数?
//  (6)派生类C的成员函数f4能否调用基类A中的成员函数f1,f2和派生类中的成员函数f3?

class A						//A为基类
{
public:
	void f1();
	int i;
protected:
	void f 2();
	int j;
private:
	int k;
};
class B : public A					//B为A的公用派生类
{
public:
	void f 3();
protected:
	int m;
private:
	int n;
};
class C : public B        			//C为B的公用派生类
{
public:
	void f4();
private:
	int p;
};
int main()
{
	A a1;                    		//a1是基类A的对象
	B b1;                      		//b1是派生类B的对象
	C c1;                     		//c1是派生类C的对象

	return 0;
}

(6) 派生类C的成员函数f4能否调用基类A中的成员函数f1,f2和派生类中的成员函数f3?

6.有以下程序结构,请分析所有成员在各类的范围内的访问属性。

【解】

//11.6
//6.有以下程序结构,请分析所有成员在各类的范围内的访问属性。

class A                      			//基类
{
public:
	void f1();
protected:
	void f2();
private:
	int i;
};

class B : public A             			// B为A的公用派生类
{
public:
	void f3();
	int k;
private:
	int m;
};

class C : protected B       				//C为B的保护派生类
{
public:
	void f4();
protected:
	int n;
private:
	int p;
};

class D : private C         				//D为C的私有派生类
{
public:
	void f5();
protected:
	int q;
private:
	int r;
};
void main()
{
	A a1;                    			//a1是基类A的对象
	B b1;                    		//b1是派生类B的对象
	C c1;                    		//c1是派生类C的对象
	D d1;                    		//d1是派生类D的对象

}

7.有以下程序,请完成下面工作:

(1) 阅读程序,写出运行时输出的结果。

(2) 然后上机运行,验证结果是否正确。

(3) 分析程序执行过程,尤其是调用构造函数的过程。

【解】

//11.7
//7.有以下程序,请完成下面工作:
//  (1)阅读程序,写出运行时输出的结果。
//  (2)然后上机运行,验证结果是否正确。
//  (3)分析程序执行过程,尤其是调用构造函数的过程。

#include 
using namespace std;
class A
{
public:
	A() { a = 0; b = 0; }
	A(int i) { a = i; b = 0; }
	A(int i, int j) { a = i; b = j; }
	void display() { cout << "a=" << a << " b=" << b; }
private:
	int a;
	int b;
};
class B : public A
{
public:
	B() { c = 0; }
	B(int i) :A(i) { c = 0; }
	B(int i, int j) :A(i, j) { c = 0; }
	B(int i, int j, int k) :A(i, j) { c = k; }
	void display1()
	{
		display();
		cout << " c=" << c << endl;
	}
private:
	int c;
};
int main()
{
	B b1;
	B b2(1);
	B b3(1, 3);
	B b4(1, 3, 5);
	b1.display1();
	b2.display1();
	b3.display1();
	b4.display1();
	return 0;
}

//a = 0 b = 0 c = 0
//a = 1 b = 0 c = 0
//a = 1 b = 3 c = 0
//a = 1 b = 3 c = 5

8.有以下程序,请完成下面工作:

(1) 阅读程序,写出运行时输出的结果。

(2) 然后上机运行,验证结果是否正确。

(3) 分析程序执行过程,尤其是调用构造函数和析构函数的过程。

【解】

//11.8
//8.有以下程序,请完成下面工作:
//  (1)阅读程序,写出运行时输出的结果。
//  (2)然后上机运行,验证结果是否正确。
//  (3)分析程序执行过程,尤其是调用构造函数和析构函数的过程。

#include 
using namespace std;
class A
{
public:
	A() { cout << "constructing A " << endl; }
	~A() { cout << "destructing A " << endl; }
};
class B :public A
{
public:
	B() { cout << "constructing B " << endl; }
	~B() { cout << "destructing B " << endl; }
};
class C :public B
{
public:
	C() { cout << "constructing C " << endl; }
	~C() { cout << "destructing C " << endl; }
};
int main()
{
	C c1;
	return 0;
}

//constructing A
//constructing B
//constructing C
//destructing C
//destructing B
//destructing A

9.分别声明Teacher(教师)类和Cadre(干部)类,采用多重继承方式由这两个类派生出新类Teacher_Cadre(教师兼干部)类。要求:

(1) 在两个基类中都包含姓名、年龄、性别、地址、电话等数据成员。

(2) 在Teacher类中还包含数据成员title(职称),在Cadre类中还包含数据成员post(职务)。在Teacher_Cadre类中还包含数据成员wages(工资)。

(3) 对两个基类中的姓名、年龄、性别、地址、电话等数据成员用相同的名字,在引用这些数据成员时,指定作用域。

(4) 在类体中声明成员函数,在类外定义成员函数。

(5) 在派生类Teacher_Cadre的成员函数show中调用Teacher类中的display函数,输出姓名、年龄、性别、职称、地址、电话,然后再用cout语句输出职务与工资。

【解】

//11.9
//9.分别声明Teacher(教师)类和Cadre(干部)类,
//  采用多重继承方式由这两个类派生出新类Teacher_Cadre(教师兼干部)类。要求:
//  (1)在两个基类中都包含姓名、年龄、性别、地址、电话等数据成员。
//  (2)在Teacher类中还包含数据成员title(职称),
//	 在Cadre类中还包含数据成员post(职务)。
//	 在Teacher_Cadre类中还包含数据成员wages(工资)。
//  (3)对两个基类中的姓名、年龄、性别、地址、电话等数据成员用相同的名字,
//	 在引用这些数据成员时,指定作用域。
//  (4)在类体中声明成员函数,在类外定义成员函数。
//  (5)在派生类Teacher_Cadre的成员函数show中调用Teacher类中的display函数,
//	 输出姓名、年龄、性别、职称、地址、电话,然后再用cout语句输出职务与工资。

#include
#include 
using namespace std;
class Teacher
{
public:
	Teacher(string nam, int a, char s, string tit, string ad, string t);	//构造函数
	void display();                            //输出姓名、性别、年龄、职称、地址、电话
protected:
	string name;
	int age;
	char sex;
	string title;
	string addr;
	string tel;
};
Teacher::Teacher(string nam, int a, char s, string tit, string ad, string t) :name(nam), age(a), sex(s), title(tit),
addr(ad), tel(t) { }	//此两行为构造函数定义
void Teacher::display()
{
	cout << "name:" << name << endl;
	cout << "age:" << age << endl;
	cout << "sex:" << sex << endl;
	cout << "title:" << title << endl;
	cout << "address:" << addr << endl;
	cout << "tel:" << tel << endl;
}
class Cadre
{
public:
	Cadre(string nam, int a, char s, string p, string ad, string t);	//构造函数
	void display();
protected:
	string name;
	int age;
	char sex;
	string post;
	string addr;
	string tel;
};
Cadre::Cadre(string nam, int a, char s, string p, string ad, string t) :name(nam), age(a), sex(s), post(p),
addr(ad), tel(t) {}                                    	//此两行为构造函数定义
void Cadre::display()
{
	cout << "name:" << name << endl;
	cout << "age:" << age << endl;
	cout << "sex:" << sex << endl;
	cout << "post:" << post << endl;
	cout << "address:" << addr << endl;
	cout << "tel:" << tel << endl;
}
class Person :public Teacher, public Cadre
{
public:
	Person(string nam, int a, char s, string tit, string p, string ad, string t, float w);
	void show();
private:
	float wage;
};
Person::Person(string nam, int a, char s, string t, string p, string ad, string tel, float w) :
	Teacher(nam, a, s, t, ad, tel), Cadre(nam, a, s, p, ad, tel), wage(w) { }	//以上两行为构造函数定义
void Person::show()
{
	Teacher::display();                                 	//指定作用域teacher类
	cout << "post:" << Cadre::post << endl;                    	//指定作用域Cadre类
	cout << "wages:" << wage << endl;
}
int main()
{
	Person person1("Wang-li", 50, 'f ', "prof.", "president", "135 Beijing Road,Shanghai",
		"(021)61234567", 1534.5);
	person1.show();
	return 0;
}

//name : Wang - li
//age : 50
//sex : f
//title :
//post:prof.
//address : 135 Beijing Road, Shanghai
//tel : (021)61234567

10.将第11.8节中的程序段加以补充完善,使之成为一个完整的程序。在程序中使用继承和组合。在定义Professor类对象prof1时给出所有数据的初值,然后修改prof1的生日数据,最后输出prof1的全部最新数据。

【解】

//11.10
//10.将第11.8节中的程序段加以补充完善,使之成为一个完整的程序。
//   在程序中使用继承和组合。在定义Professor类对象prof1时给出所有数据的初值,
//   然后修改prof1的生日数据,最后输出prof1的全部最新数据。

#include 
#include 
using namespace std;
class Teacher                            		//教师类
{
public:
	Teacher(int, char[], char);             			//声明构造函数
	void display();                         		//声明输出函数
private:
	int num;
	char name[20];
	char sex;
};
Teacher::Teacher(int n, char nam[], char s)    		//定义构造函数
{
	num = n;
	strcpy(name, nam);
	sex = s;
}
void Teacher::display()                     		//定义输出函数
{
	cout << "num:" << num << endl;
	cout << "name:" << name << endl;
	cout << "sex:" << sex << endl;
}
class BirthDate                              		//生日类
{
public:
	BirthDate(int, int, int);                  		//声明构造函数
	void display();                          		//声明输出函数
	void change(int, int, int);                 		//声明修改函数
private:
	int year;
	int month;
	int day;
};
BirthDate::BirthDate(int y, int m, int d)       			//定义构造函数
{
	year = y;
	month = m;
	day = d;
}
void BirthDate::display()                    		//定义输出函数
{
	cout << "birthday:" << month << "/" << day << "/" << year << endl;
}
void BirthDate::change(int y, int m, int d)   			//定义修改函数
{
	year = y;
	month = m;
	day = d;
}
class Professor :public Teacher                   	//教授类
{
public:
	Professor(int, char[], char, int, int, int, float);   		//声明构造函数
	void display();                               	//声明输出函数
	void change(int, int, int);                        	//声明修改函数
private:
	float area;                            		//住房面积
	BirthDate birthday;                    		//定义BirthDate类的对象作为数据成员
};
Professor::Professor(int n, char nam[20], char s, int y, int m, int d, float a) :
	Teacher(n, nam, s), birthday(y, m, d), area(a) { }        	//定义构造函数

void Professor::display()                          	//定义输出函数
{
	Teacher::display();
	birthday.display();
	cout << "area:" << area << endl;
}
void Professor::change(int y, int m, int d)           	//定义修改函数
{
	birthday.change(y, m, d);
}
int main()
{
	Professor prof1(3012, "Zhang", 'f ', 1949, 10, 1, 125.4);  	//定义Professor对象prof1
	cout << endl << " The original data:" << endl;
	prof1.display();                                 	//调用prof1对象的display函数
	cout << endl << "The new data:" << endl;
	prof1.change(1950, 6, 1);                          	//调用prof1对象的change函数
	prof1.display();                                	//调用prof1对象的display函数
	return 0;
}

//The original data :
//num:3012
//name : Zhang
//sex : f
//birthday : 10 / 1 / 1949
//area : 125.4
//
//The new data :
//num : 3012
//name : Zhang
//sex : f
//birthday : 6 / 1 / 1950
//area : 125.4

你可能感兴趣的:(C++程序设计(第3版)谭浩强,课后习题答案,c++)