C++ Primer Plus(第六版)第十五章课后习题

C++ Primer Plus(第六版)第十五章课后习题

15.8.1

tv.h

#ifndef TV_H_
#define TV_H_
class Remote;
class Tv
{
private:
	int state;
	int volume;
	int maxchannel;
	int channel;
	int mode;
	int input;
public:
	friend class Remote;
	enum {Off, On};
	enum {MinVal, MaxVal=20};
	enum {Antenna, Cable};//antenna 天线, cable 电缆
	enum {TV, DVD};
	Tv(int s=Off, int mc=125): state(s), volume(5),maxchannel(mc), channel(2), mode(Cable), input(TV) {}
	void onoff() { state=(state==On)?Off: On; }
	bool ison() const {return state==On;}
	bool volup();
	bool voldown();
	void chanup(); 
	void chandown();
	void set_mode() {mode=(mode==Antenna)?Cable:Antenna;}
	void set_input() {input=(input==TV)?Off:On;}
	void settings() const;
	void Remote_set(Remote &r);
};
class Remote
{
private:
	int mode;
	int mode1;
public:
	friend class Tv;
	enum {Interactive, Normal};
	Remote(int m=Tv::TV, int n=Normal): mode(m), mode1(n) {}
	void Show(); 
	bool volup(Tv &t) {return t.volup();}
	bool voldowm(Tv &t) {return t.voldown();}
	void onoff(Tv &t) { t.onoff();}
	void chanup(Tv &t) { t.chanup();}
	void chandown(Tv &t) { t.chandown();}
	void set_chan(Tv &t, int c) { t.channel=c;}
	void set_mode(Tv &t) { t.set_mode();}
	void set_input(Tv &t) { t.set_input();}
};
#endif

tv.cpp

#include <iostream>
#include "tv.h"
bool Tv::volup()
{
	if(volume<MaxVal)
	{
		volume++;
		return true;
	}
	else
		return false;
}
bool Tv::voldown()
{
	if(volume>MinVal)
	{
		volume--;
		return true;
	}
	else 
		return false;
}
void Tv::chanup()
{
	if(channel<maxchannel)
		channel++;
	else 
		channel=0;
}
void Tv::chandown()
{
	if(channel>1)
		channel--;
	else
		channel=maxchannel;
}
void Tv::settings() const
{
	using std::cout;
	using std::endl;
	cout << "Tv is " << (state==Off?"Off": "On") << endl;
	if(state==On)
	{
		cout << "Volume setting =" << volume << endl;
		cout << "Channel setting =" << channel << endl;
		cout << "Mode = "
			<< (mode==Antenna?"antenna": "cable") << endl;
		cout << "Input = "
			<< (input==TV? "TV": "DVD") << endl;
	}
}
void Tv::Remote_set(Remote &r)
{
	if(state==On)
	{
		r.mode1=(r.mode1==Remote::Interactive?Remote::Normal: Remote::Interactive);
	}
}
void Remote::Show()
{
	using std::cout;
	using std::endl;
	cout << "Remote mode1: " << (mode1==Normal?"Normal": "Interactive") << endl;
}

use_tv.cpp

#include <iostream>
#include "tv.h"
int main()
{
	using std::cout;
	Tv s42;
	cout << "Initial settings for 42\" TV: \n";
	s42.settings();
	s42.onoff();
	s42.chanup();
	cout << "\nAdjusted settings for 42\" TV: \n";
	s42.chanup();
	s42.settings();

	Remote grey;

	grey.set_chan(s42, 10);
	grey.volup(s42);
	cout << "\n42\" settings after using remote:\n";
	s42.settings();

	Tv s58(Tv::On);
	s58.set_mode();
	grey.set_chan(s58,28);
	cout << "\n58\" settings: \n";
	s58.settings();
	grey.Show();
	s58.Remote_set(grey);
	grey.Show();
	return 0;
}

15.11(此处提供15.8.2需要的程序15.11)

exc_mean.h

#ifndef EXC_MEAN_H
#define EXC_MEAN_H
#include <iostream>
class bad_hmean
{
private:
	double v1;
	double v2;
public:
	bad_hmean(double a=0, double b=0): v1(a), v2(b){}
	void mesg();
};

inline void bad_hmean::mesg()
{
	std::cout << "hmean(" << v1 << ", " << v2 << "): "
		<< "invalid arguments: a=-b\n";
}

class bad_gmean
{
public:
	double v1,v2;
	bad_gmean(double a=0, double b=0): v1(a), v2(b) {}
	const char *mesg();
};

inline const char *bad_gmean::mesg()
{
	return "gmean() argument should be >=0\n";
}
#endif

error4.cpp

#include <iostream>
#include <cmath>
#include "exc_mean.h"
double hmean(double a, double b);
double gmean(double a, double b);
int main()
{
	using std::cout; 
	using std::cin;
	using std::endl; 
	double x, y, z;
	cout << "Enter two numbers: ";
	while(cin >> x >> y)
	{
		try
		{
			z=hmean(x, y);
			cout << "Harmonic mean of " << x << " and " << y
				<< " is " << z << endl;
			cout << "Geometric mean of " << x << " and " << y
				<< " is " << gmean(x, y) << endl;
			cout << "Enter next set of numbers <q to quit>: ";
		}
		catch(bad_hmean &bg)
		{
			bg.mesg();
			cout << "Try again.\n";
			continue;
		}
		catch(bad_gmean &hg)
		{
			cout << hg.mesg();
			cout << "Values used: " << hg.v1 << ", "
				<< hg.v2 << endl;
			cout << "Sorry, you don't get to play any more.\n";
			break;
		}
	}
	cout << "Bye!\n";
	return 0;
}
double hmean(double a, double b)
{
	if(a==-b)
		throw bad_hmean(a, b);
	return 2.0*a*b/(a+b);
}
double gmean(double a, double b)
{
	if(a<0||b<0)
		throw bad_gmean(a, b);
	return std::sqrt(a*b);
}

15.8.2

error.h

#ifndef DD
#define DD
#include <iostream>
#include <stdexcept>
class bad_hmean: public std::logic_error
{
public:
	bad_hmean(): std::logic_error("invalid argument: a=-b\n"){}
};

class bad_gmean: public std::logic_error
{
public:
	bad_gmean(): std::logic_error("gmean() arguments should be >=0\n"){}
};

#endif

error.cpp

#include <iostream>
#include <cmath>
#include "error.h"
double hmean(double a, double b);
double gmean(double a, double b);
int main()
{
	using std::cout; 
	using std::cin;
	using std::endl; 
	double x, y, z;
	cout << "Enter two numbers: ";
	while(cin >> x >> y)
	{
		try
		{
			z=hmean(x, y);
			cout << "Harmonic mean of " << x << " and " << y
				<< " is " << z << endl;
			cout << "Geometric mean of " << x << " and " << y
				<< " is " << gmean(x, y) << endl;
			cout << "Enter next set of numbers <q to quit>: ";
		}
		catch(bad_hmean &bg)
		{
			cout << bg.what();
			cout << "Try again.\n";
			continue;
		}
		catch(bad_gmean &hg)
		{
			cout << hg.what();
			cout << "Sorry, you don't get to play any more.\n";
			break;
		}
	}
	cout << "Bye!\n";
	return 0;
}
double hmean(double a, double b)
{
	if(a==-b)
		throw bad_hmean();
	return 2.0*a*b/(a+b);
}
double gmean(double a, double b)
{
	if(a<0||b<0)
		throw bad_gmean();
	return std::sqrt(a*b);
}

15.8.3

error.h

#ifndef DD
#define DD
#include <iostream>
#include <stdexcept>
#include <string>
using std::string;
using std::cout;
class bad_mean: public std::logic_error
{
private:
	double v1;
	double v2;
	string s;
public:
	bad_mean(double a=0, double b=0, string s="Error!"): v1(a), v2(b), std::logic_error(s) {}
	virtual void mesg()=0;
};
void bad_mean::mesg()
{
	cout << v1 << ", " << v2 << " are invalid arguments\n"; 
	cout << what() << std::endl;
}
class bad_hmean: public bad_mean
{
public:
	bad_hmean(double a=0, double b=0, string s="invalid arguments: a=-b"): bad_mean(a, b, s) {}
	void mesg();
};
void bad_hmean::mesg()
{
	bad_mean::mesg();
	cout << "Wrong function is hmean."<<std::endl;
}
class bad_gmean: public bad_mean
{
public:
	bad_gmean(double a=0, double b=0, string s="gmean() arguments should be >=0"): bad_mean(a, b, s) {}
	void mesg();
};
void bad_gmean::mesg()
{
	bad_mean::mesg();
	cout << "Wrong function is gmean."<<std::endl;
}
#endif

error.cpp

#include <iostream>
#include <cmath>
#include "error.h"
double hmean(double a, double b);
double gmean(double a, double b);
int main()
{
	using std::cout; 
	using std::cin;
	using std::endl; 
	double x, y, z;
	cout << "Enter two numbers: ";
	while(cin >> x >> y)
	{
		try
		{
			z=hmean(x, y);
			cout << "Harmonic mean of " << x << " and " << y
				<< " is " << z << endl;
			cout << "Geometric mean of " << x << " and " << y
				<< " is " << gmean(x, y) << endl;
			cout << "Enter next set of numbers <q to quit>: ";
		}
		catch(bad_mean &bg)
		{
			bg.mesg();
			break;
		}
	}
	cout << "Bye!\n";
	return 0;
}
double hmean(double a, double b)
{
	if(a==-b)
		throw bad_hmean(a, b);
	return 2.0*a*b/(a+b);
}
double gmean(double a, double b)
{
	if(a<0||b<0)
		throw bad_gmean(a, b);
	return std::sqrt(a*b);
}

15.16(此处提供15.8.4需要的程序15.16)

sales.h

#include <stdexcept>
#include <string>
class Sales
{
public:
	enum {MONTHS=12};
	class bad_index: public std::logic_error
	{
	private:
		int bi;
	public:
		explicit bad_index(int ix, const std::string &s="Index error in Sales object\n");
		int bi_val() const { return bi;}
		virtual ~bad_index() throw() {}
	};
	explicit Sales(int yy=0);
	Sales(int yy, const double *gr, int n);
	virtual ~Sales() {}
	int Year() const { return year;}
	virtual double operator[](int i) const;
	virtual double & operator[](int i);
private:
	double gross[MONTHS];
	int year;
};
class LabeledSales: public Sales
{
public:
	class nbad_index: public Sales::bad_index
	{
	private:
		std::string lbl;
	public:
		nbad_index(const std::string &lb, int ix, const std::string &s="Index error in LabeledSales object\n");
		const std::string &label_val() const { return lbl;}
		virtual ~nbad_index() throw() {}
	};
	explicit LabeledSales(const std::string &lb="none", int yy=0);
	LabeledSales(const std::string &lb, int yy, const double *gr, int n);
	virtual ~LabeledSales() {}
	const std::string &Label() const { return label;}
	virtual double operator[](int i) const;
	virtual double & operator[](int i);
private:
	std::string label;
};

sales.cpp

#include "sales.h"
using std::string;
Sales::bad_index::bad_index(int ix, const string &s): std::logic_error(s), bi(ix)
{
}
Sales::Sales(int yy)
{
	year=yy;
	for(int i=0;i<MONTHS;i++)
		gross[i]=0;
}
Sales::Sales(int yy, const double *gr, int n)
{
	year=yy;
	int lim=(n<MONTHS)?n:MONTHS;
	int i;
	for(i=0;i<lim;i++)
		gross[i]=gr[i];
	for(;i<MONTHS;i++)
		gross[i]=0;
}
double Sales::operator[](int i) const
{
	if(i<0||i>=MONTHS)
		throw bad_index(i);
	return gross[i];
}
double &Sales::operator[](int i) 
{
	if(i<0||i>=MONTHS)
		throw bad_index(i);
	return gross[i];
}
LabeledSales::nbad_index::nbad_index(const string &lb, int ix, const string &s): Sales::bad_index(ix, s)
{
	lbl=lb;
}
LabeledSales::LabeledSales(const string &lb, int yy): Sales(yy)
{
	label=lb;
}
LabeledSales::LabeledSales(const string &lb, int yy, const double *gr, int n): Sales(yy, gr, n)
{
	label=lb;
}
double LabeledSales::operator[](int i) const
{
	if(i<0||i>=MONTHS)
		throw nbad_index(Label(), i);
	return Sales::operator[](i);
}
double &LabeledSales::operator[](int i)
{
	if(i<0||i>=MONTHS)
		throw nbad_index(Label(), i);
	return Sales::operator[](i);
}

use_sales.cpp

#include <iostream>
#include "sales.h"
int main()
{
	using std::cout;
	using std::cin;
	using std::endl;
	double vals1[12]=
	{
		1220, 1100, 1122, 2212, 1232, 2334, 2884, 2393, 3302, 2922, 3002, 3544
	};
	double vals2[12]=
	{
		12, 11, 22, 21, 32, 34, 28, 29, 33, 29, 32, 35
	};
	Sales sales1(2011, vals1, 12);
	LabeledSales sales2("Blogstar", 2012, vals2, 12);
	cout << "First try block:\n";
	try
	{
		int i;
		cout << "Year= " << sales1.Year() << endl;
		for(i=0;i<12;i++)
		{
			cout << sales1[i] << ' ';
			if(i%6==5)
				cout << endl;
		} 
		cout << "Year= " << sales2.Year() << endl;
		cout << "Label= " << sales2.Label() << endl;
		for(i=0;i<=12;i++)
		{
			cout << sales2[i] << ' ';
			if(i%6==5)
				cout << endl;
		}
		cout << "End of try block 1.\n";
	}
	catch(LabeledSales::nbad_index &bad)
	{
		cout << bad.what();
		cout << "Company: " << bad.label_val() << endl;
		cout << "bad index: " << bad.bi_val() << endl;
	}
	catch(Sales::bad_index &bad)
	{
		cout << bad.what();
		cout << "bad index: " << bad.bi_val() << endl;
	}
	cout << "\nNext try block:\n";
	try
	{
		sales2[2]=37.5;
		sales1[20]=23345;
		cout << "End of try block 2.\n";
	}
	catch(Sales::bad_index &bad)
	{
		cout << bad.what();
		cout << "bad index: " << bad.bi_val() << endl;
	}
	cout << "done\n";
	return 0;
}

15.8.4

sales.h

#include <stdexcept>
#include <string>
class Sales
{
public:
	enum {MONTHS=12};
	class bad_index: public std::logic_error
	{
	private:
		int bi;
	public:
		explicit bad_index(int ix, const std::string &s="Index error in Sales object\n");
		int bi_val() const { return bi;}
		virtual ~bad_index() throw() {}
	};
	explicit Sales(int yy=0);
	Sales(int yy, const double *gr, int n);
	virtual ~Sales() {}
	int Year() const { return year;}
	virtual double operator[](int i) const;
	virtual double & operator[](int i);
private:
	double gross[MONTHS];
	int year;
};
class LabeledSales: public Sales
{
public:
	class nbad_index: public Sales::bad_index
	{
	private:
		std::string lbl;
	public:
		nbad_index(const std::string &lb, int ix, const std::string &s="Index error in LabeledSales object\n");
		const std::string &label_val() const { return lbl;}
		virtual ~nbad_index() throw() {}
	};
	explicit LabeledSales(const std::string &lb="none", int yy=0);
	LabeledSales(const std::string &lb, int yy, const double *gr, int n);
	virtual ~LabeledSales() {}
	const std::string &Label() const { return label;}
	virtual double operator[](int i) const;
	virtual double & operator[](int i);
private:
	std::string label;
};

sales.cpp

#include "sales.h"
using std::string;
Sales::bad_index::bad_index(int ix, const string &s): std::logic_error(s), bi(ix)
{
}
Sales::Sales(int yy)
{
	year=yy;
	for(int i=0;i<MONTHS;i++)
		gross[i]=0;
}
Sales::Sales(int yy, const double *gr, int n)
{
	year=yy;
	int lim=(n<MONTHS)?n:MONTHS;
	int i;
	for(i=0;i<lim;i++)
		gross[i]=gr[i];
	for(;i<MONTHS;i++)
		gross[i]=0;
}
double Sales::operator[](int i) const
{
	if(i<0||i>=MONTHS)
		throw bad_index(i);
	return gross[i];
}
double &Sales::operator[](int i) 
{
	if(i<0||i>=MONTHS)
		throw bad_index(i);
	return gross[i];
}
LabeledSales::nbad_index::nbad_index(const string &lb, int ix, const string &s): Sales::bad_index(ix, s)
{
	lbl=lb;
}
LabeledSales::LabeledSales(const string &lb, int yy): Sales(yy)
{
	label=lb;
}
LabeledSales::LabeledSales(const string &lb, int yy, const double *gr, int n): Sales(yy, gr, n)
{
	label=lb;
}
double LabeledSales::operator[](int i) const
{
	if(i<0||i>=MONTHS)
		throw nbad_index(Label(), i);
	return Sales::operator[](i);
}
double &LabeledSales::operator[](int i)
{
	if(i<0||i>=MONTHS)
		throw nbad_index(Label(), i);
	return Sales::operator[](i);
}

usesales.cpp

#include <iostream>
#include "sales.h"
int main()
{
	using std::cout;
	using std::cin;
	using std::endl;
	double vals1[12]=
	{
		1220, 1100, 1122, 2212, 1232, 2334, 2884, 2393, 3302, 2922, 3002, 3544
	};
	double vals2[12]=
	{
		12, 11, 22, 21, 32, 34, 28, 29, 33, 29, 32, 35
	};
	Sales sales1(2011, vals1, 12);
	LabeledSales sales2("Blogstar", 2012, vals2, 12);
	cout << "First try block:\n";
	try
	{
		int i;
		cout << "Year= " << sales1.Year() << endl;
		for(i=0;i<12;i++)
		{
			cout << sales1[i] << ' ';
			if(i%6==5)
				cout << endl;
		} 
		cout << "Year= " << sales2.Year() << endl;
		cout << "Label= " << sales2.Label() << endl;
		for(i=0;i<=12;i++)
		{
			cout << sales2[i] << ' ';
			if(i%6==5)
				cout << endl;
		}
		cout << "End of try block 1.\n";
	}
	catch(Sales::bad_index &bad)
	{
		LabeledSales::nbad_index *p;
		cout << bad.what();
		if(p=dynamic_cast<LabeledSales::nbad_index *>(&bad))
			cout << "Company: " << p->label_val() << endl;
		cout << "bad index: " << bad.bi_val() << endl;
	}
	
	cout << "\nNext try block:\n";
	try
	{
		sales2[2]=37.5;
		sales1[20]=23345;
		cout << "End of try block 2.\n";
	}
	
	catch(Sales::bad_index &bad)
	{
		LabeledSales::nbad_index *p;
		cout << bad.what();
		if(p=dynamic_cast<LabeledSales::nbad_index *>(&bad))
			cout << "Company: " << p->label_val() << endl;
		cout << "bad index: " << bad.bi_val() << endl;
	}
	cout << "done\n";
	return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值