14-1
参考14.19
winec.h
#ifndef WINEC_H_
#define WINEC_H_
#include <string>
#include <valarray>
using std::string;template<class T1, class T2>
class Pair
{
private:T1 year;T2 bottles;
public:Pair() {};Pair(const T1 y, const T2 b) :year(y), bottles(b) {}T1 first() const { return year; }T2 second() const { return bottles; }int Sum();void Set(const T1 y, const T2 b);void Show(int y);
};template<class T1, class T2>
inline int Pair<T1, T2>::Sum()
{return bottles.sum();
}template<class T1, class T2>
inline void Pair<T1, T2>::Set(const T1 y, const T2 b)
{year = y;bottles = b;
}template<class T1, class T2>
inline void Pair<T1, T2>::Show(int y)
{for (int i = 0; i < y; i++){std::cout << "\t" << first()[i] << "\t" << second()[i] << std::endl;}
}typedef std::valarray<int> ArrayInt;
typedef Pair<ArrayInt, ArrayInt> PairArray;class Wine
{
private:int yrs;string fullname;PairArray pa;
public:Wine(const char* l, int y, const int yr[], const int bot[]);Wine(const char* l, int y);Wine();void GetBottles();string Label();int sum();void Show();
};#endif // !WINEC_H_
winec.cpp
#include <iostream>
#include <string>
#include "winec.h"
using std::cout;
using std::cin;
using std::endl;Wine::Wine(const char* l, int y, const int yr[], const int bot[])
{fullname = l;yrs = y;pa.Set(ArrayInt(yr, yrs), ArrayInt(bot, yrs));
}Wine::Wine(const char* l, int y)
{fullname = l;yrs = y;
}Wine::Wine()
{fullname = "None wine";yrs = 0;
}void Wine::GetBottles()
{cout << "Enter " << fullname << " for " << yrs << " year(s):\n";ArrayInt yr(yrs), bt(yrs);for (int i = 0; i < yrs; i++){cout << "Enter the year: ";cin >> yr[i];cout << "Enter the bottles: ";cin >> bt[i];}while (cin.get() != '\n')continue;pa.Set(yr, bt);
}string Wine::Label()
{return fullname;
}int Wine::sum()
{return pa.Sum();
}void Wine::Show()
{cout << "Wine: " << fullname << endl;cout << "\tyear\tbottles" << endl;pa.Show(yrs);
}
main.cpp
#include <iostream>
#include "winec.h"int main( void )
{using std::cin;using std::cout;using std::endl;cout << "Enter name of wine: ";char lab[50];cin.getline(lab, 50);cout << "Enter number of years: ";int yrs;cin >> yrs;Wine holding(lab, yrs);holding.GetBottles();holding.Show();const int YRS = 3;int y[YRS] = { 1993,1995,1998 };int b[YRS] = { 48,60,72 };Wine more("Gushing Grape Red", YRS, y, b);more.Show();cout << "Total bottles for " << more.Label()<< ": " << more.sum() << endl;cout<<"Bye\n";return 0;
}
14-2
参考14.19和14.4
winec.h
#ifndef WINEC_H_
#define WINEC_H_
#include <string>
#include <valarray>
using std::string;template<class T1, class T2>
class Pair
{
private:T1 year;T2 bottles;
public:Pair() {};Pair(const T1 y, const T2 b) :year(y), bottles(b) {}T1 first() const { return year; }T2 second() const { return bottles; }void Set(const T1 y, const T2 b);void Show(int y);
};template<class T1, class T2>
inline void Pair<T1, T2>::Set(const T1 y, const T2 b)
{year = y;bottles = b;
}template<class T1, class T2>
inline void Pair<T1, T2>::Show(int y)
{for (int i = 0; i < y; i++){std::cout << "\t" << year[i] << "\t" << bottles[i] << std::endl;}
}
typedef std::valarray<int> ArrayInt;
typedef Pair<ArrayInt, ArrayInt> PairArray;class Wine:private string, private PairArray
{
private:int yrs;string fullname;
public:Wine(const char* l, int y, const int yr[], const int bot[]);Wine(const char* l, int y);Wine();void GetBottles();string Label();int sum();void Show();
};#endif // !WINEC_H_
winec.cpp
#include <iostream>
#include <string>
#include "winec.h"
using std::cout;
using std::cin;
using std::endl;Wine::Wine(const char* l, int y, const int yr[], const int bot[]):string(l), PairArray(ArrayInt(yr,y),ArrayInt(bot,y))
{fullname = l;yrs = y;
}Wine::Wine(const char* l, int y):string(l),PairArray(ArrayInt(y), ArrayInt(y))
{fullname = l;yrs = y;
}Wine::Wine():string("Null"), PairArray(ArrayInt(0, 0), ArrayInt(0, 0))
{fullname = "Null";yrs = 0;
}void Wine::GetBottles()
{cout << "Enter " << fullname << " for " << yrs << " year(s):\n";ArrayInt yr(yrs), bt(yrs);for (int i = 0; i < yrs; i++){cout << "Enter the year: ";cin >> yr[i];cout << "Enter the bottles: ";cin >> bt[i];}while (cin.get() != '\n')continue;PairArray::Set(yr, bt);
}string Wine::Label()
{return (const std::string&) * this;
}int Wine::sum()
{return PairArray::second().sum();
}void Wine::Show()
{cout << "Wine: " << (const string)*this << endl;cout << "\tYear\tBotteles" << endl;for (int i = 0; i < yrs; ++i)cout << "\t" << PairArray::first()[i] << "\t" << PairArray::second()[i] << endl;
}
14-3
vs2019,有个问题,char* Singer::pv[Singer::Vtypes] = { “other”, “alto”, “contralto”, “soprano”, “bass”, “baritone”, “tenor” };,会报错const char 类型的值不能用于初始化char* 类型的实体。
网上搜索别人的答案,复制粘贴到里面,也提示有这个错误。
网上搜索发现解决方法是项目->属性->C/C+±>语言->符合模式,将符合模式由是改为否,确实有用。
想了想,这大概是因为把char[] 赋值给了char*,虽然差不多,但是编译器不允许?于是就有一个笨办法,先声明一个char temp[]类型,再把数组名赋值给pv里面的指针,这样就是把char赋值给char了,也不会报错。
char temp1[] = “other”;
char temp2[] = “alto”;
char temp3[] = “contralto”;
char temp4[] = “soprano”;
char temp5[] = “bass”;
char temp6[] = “baritone”;
char temp7[] = “tenor”;
char* Singer::pv[Singer::Vtypes] = { temp1, temp2, temp3, temp4, temp5, temp6, temp7 };
QueueTp.h
#ifndef QUEUETP_H_
#define QUEUETP_H_template <typename T>
class QueueTp
{
private:static const int LEN = 10;T* listHead;T* listTail;T* data;
public:QueueTp(int len = LEN) { data = new T[len]; listHead = listTail = data; }~QueueTp() { delete[] data; }bool enQueue(const T& item);bool deQueue(T& item);T newQueue() const { return *(listTail - 1); }bool isFull() const { return listTail == data + sizeof(data); }bool isEmpty() const { return listTail == listHead; }
};template <typename T>
bool QueueTp<T>::enQueue(const T& item)
{if (isFull())return false;*listTail = item;listTail++;return true;
}template <typename T>
bool QueueTp<T>::deQueue(T& item)
{if (isFull())return false;item = *listHead;listHead++;return true;
}#endif // !QUEUETP_H_
workermi.h
#ifndef WORKERMI_H_
#define WORKERMI_H_#include <string>class Worker
{
private:std::string fullname;long id;
protected:virtual void Data() const;virtual void Get();
public:Worker() : fullname("no one"), id(0L) {}Worker(const std::string& s, long n) :fullname(s), id(n) {}virtual ~Worker() = 0;virtual void Set() = 0;virtual void Show() const = 0;
};class Waiter :virtual public Worker
{
private:int panache;
protected:void Data() const;void Get();
public:Waiter() :Worker(), panache(0) {}Waiter(const std::string& s, long n, int p = 0) :Worker(s, n), panache(p) {}Waiter(const Worker& wk, int p = 0) :Worker(wk), panache(p) {}void Set();void Show() const;
};class Singer :virtual public Worker
{
protected:enum { other, alto, contralto, soprano, bass, baritone, tenor };enum { Vtypes = 7 };void Data() const;void Get();
private:static char* pv[Vtypes];int voice;
public:Singer() :Worker(), voice(other) {}Singer(const std::string& s, long n, int v = other) :Worker(s, n), voice(v) {}Singer(const Worker& wk, int v = other) :Worker(wk), voice(v) {}void Set();void Show() const;
};class SingingWaiter :public Singer, public Waiter
{
protected:void Data() const;void Get();
public:SingingWaiter() {}SingingWaiter(const std::string& s, long n, int p = 0, int v = other) :Worker(s, n), Waiter(s, n, p), Singer(s, n, v) {}SingingWaiter(const Worker& wk, int p = 0, int v = other) :Worker(wk), Waiter(wk, p), Singer(wk, v) {}SingingWaiter(const Worker& wt, int v = other) :Worker(wt), Waiter(wt), Singer(wt, v) {}SingingWaiter(const Singer& wt, int p = 0) :Worker(wt), Waiter(wt, p), Singer(wt) {}void Set();void Show() const;
};
#endif // !WORKERMI_H_
workermi.cpp
#include "workermi.h"
#include <iostream>using std::cout;
using std::cin;
using std::endl;Worker::~Worker() {}void Worker::Data() const
{cout << "Name: " << fullname << endl;cout << "Employee ID: " << id << endl;
}void Worker::Get()
{getline(cin, fullname);cout << "Enter worker's ID: ";cin >> id;while (cin.get() != '\n')continue;
}void Waiter::Set()
{cout << "Enter waiter's name: ";Worker::Get();Get();
}void Waiter::Show() const
{cout << "Category: waiter\n";Worker::Data();Data();
}void Waiter::Data() const
{cout << "Panache rating: " << panache << endl;
}void Waiter::Get()
{cout << "Enter waiter's panache rating: ";cin >> panache;while (cin.get() != '\n')continue;
}char temp1[] = "other";
char temp2[] = "alto";
char temp3[] = "contralto";
char temp4[] = "soprano";
char temp5[] = "bass";
char temp6[] = "baritone";
char temp7[] = "tenor";
char* Singer::pv[Singer::Vtypes] = { temp1, temp2, temp3, temp4, temp5, temp6, temp7 };void Singer::Set()
{cout << "Enter singer's name: ";Worker::Get();Get();
}void Singer::Show() const
{cout << "Category: singer\n";Worker::Data();Data();
}void Singer::Data() const
{cout << "Vocal range: " << pv[voice] << endl;
}void Singer::Get()
{cout << "Enter number for singer's vocal range:\n";int i;for (i = 0; i < Vtypes; i++){cout << i << ": " << pv[i] << " ";if (i % 4 == 3)cout << endl;}if (i % 4 != 0)cout << endl;cin >> voice;while (cin.get() != '\n')continue;
}void SingingWaiter::Data() const
{Singer::Data();Waiter::Data();
}void SingingWaiter::Get()
{Waiter::Get();Singer::Get();
}void SingingWaiter::Set()
{cout << "Enter singing waiter's name: ";Worker::Get();Get();
}void SingingWaiter::Show() const
{cout << "Category: singing waiter\n";Worker::Data();Data();
}
main.cpp
#include <iostream>
#include <cstring>
#include "workermi.h"
#include "queuetp.h"int main()
{using std::cin;using std::cout;using std::endl;using std::strchr;QueueTp<Worker*> lolas;int ct;while(!lolas.isFull()){char choice;cout << "Enter the employee category:\n"<< "w: waiter s:singer "<< "t: singing waiter q: quit\n";cin >> choice;while (strchr("wstq", choice) == NULL){cout << "Please enter a w, s, t, or q: ";cin >> choice;}if (choice == 'q')break;switch (choice){case 'w': lolas.enQueue(new Waiter);break;case 's':lolas.enQueue(new Singer);break;case 't':lolas.enQueue(new SingingWaiter);break;}cin.get();lolas.newQueue()->Set();}cout << "\nHere is your staff:\n";Worker* wrk;while(!lolas.isEmpty()){lolas.deQueue(wrk);cout << endl;wrk->Show();delete wrk;}cout << "Bye.\n";return 0;
}
14-4
Person.h
#ifndef PERSON_H_
#define PERSON_H_
#include <iostream>
#include <string>class Person
{
private:std::string firstname;std::string lastname;
protected:virtual void Data() const;virtual void Get();
public:Person() :firstname("Null"), lastname("Null") {};Person(std::string fname, std::string lname) :firstname(fname), lastname(lname) {};virtual ~Person() = 0;virtual void Set() = 0;virtual void Show() const = 0;
};class Gunslinger :virtual public Person
{
private:double time;int num;
protected:void Data() const;void Get();
public:Gunslinger() : Person(), time(0.0), num(0) {};Gunslinger(std::string fn, std::string ln, double ti, int nu) :Person(fn, ln), time(ti), num(nu) {};Gunslinger(Person& p, double ti, int nu) :Person(p), time(ti), num(nu) {};double Draw() { return time; }void Set();void Show() const;
};class PokerPlayer :virtual public Person
{
private:int card;
protected:void Data() const;void Get();
public:PokerPlayer() :Person(), card(1) {};PokerPlayer(std::string fn, std::string ln, int ca) :Person(fn, ln), card(ca) {};PokerPlayer(Person& p, int ca) :Person(p), card(ca) {};int Draw() { return card; }void Set();void Show() const;
};class BadDude :public Gunslinger, public PokerPlayer
{
protected:void Data() const;void Get();
public:BadDude() {};BadDude(std::string fn, std::string ln, double ti = 0.0, int nu = 0, int ca = 1):Person(fn, ln), Gunslinger(fn, ln, ti, nu), PokerPlayer(fn, ln, ca) {}BadDude(Person& p, double ti, int nu, int ca):Person(p), Gunslinger(p, ti, nu), PokerPlayer(p, ca) {}BadDude(Gunslinger& gs, int ca):Person(gs), Gunslinger(gs), PokerPlayer(gs, ca) {}BadDude(PokerPlayer& pp, double ti, int nu):Person(pp), Gunslinger(pp, ti, nu), PokerPlayer(pp) {}double Gdraw() { return Gunslinger::Draw(); }int Cdraw() { return PokerPlayer::Draw(); }void Set();void Show() const;
};
#endif // !PERSON_H_
Person.cpp
#include "Person.h"
#include<iostream>
#include<string>
using std::string;
using std::cout;
using std::endl;
using std::cin;Person::~Person() {}void Person::Data() const
{cout << "Firstname: " << firstname << endl;cout << "Lastname: " << lastname << endl;
}void Person::Get()
{cout << "Enter person's firstname:";getline(cin, firstname);cout << "Enter person's lastname:";getline(cin, lastname);
}void Gunslinger::Data() const
{cout << "Time: " << endl;cout << "Num of scotch: " << endl;
}void Gunslinger::Get()
{cout << "Please enter time: " << endl;cin >> time;cout << "Please enter num of scotch: " << endl;cin >> num;while (cin.get() != '\n')continue;
}void Gunslinger::Set()
{Person::Get();Get();cout << endl;
}void Gunslinger::Show() const
{cout << "Category:Gunslinger\n";Person::Data();Data();
}void PokerPlayer::Data() const
{cout << "Card: " << card;
}void PokerPlayer::Get()
{cout << "Please enter card: " << endl;cin >> card;while (cin.get() != '\n')continue;
}void PokerPlayer::Set()
{Person::Get();Get();cout << endl;
}void PokerPlayer::Show() const
{cout << "Gategory: PokerPlayer\n";Person::Data();Data();
}void BadDude::Data() const
{Gunslinger::Data();PokerPlayer::Data();
}void BadDude::Get()
{Gunslinger::Get();PokerPlayer::Get();
}void BadDude::Set()
{Person::Get();Get();cout << endl;
}void BadDude::Show() const
{Person::Data();Data();
}
main.cpp
#include <iostream>
#include <cstring>
#include "Person.h"
#include "QueueTp.h"const int SIZE = 5;int main()
{using std::cin;using std::cout;using std::endl;using std::strchr;Person* lolas[SIZE];int ct;int number = 1;for (ct = 0; ct < SIZE; ct++) {char choice;cout << "[ Enter the employee category: ]\n"<< "g: Gunslinger p: PokerPlayer "<< "b: BadDude q: quit\n";cin >> choice;while (strchr("gpbq", choice) == NULL) {cout << "Please enter a g, p, b, or q: ";cin >> choice;}if ('q' == choice)break;number += 5;switch (choice) {case 'g': lolas[ct] = new Gunslinger("Guns", "Linger", number, 3);break;case 'p': lolas[ct] = new PokerPlayer("Poker", "Player",2);break;case 'b': lolas[ct] = new BadDude("Bad", "Dude", number, 5);break;}cin.get();}cout << "\nHere is your staff:\n";int i;for (i = 0; i < ct; i++) {cout << endl;lolas[i]->Show();}for (i = 0; i < ct; i++)delete lolas[i];BadDude* badd = new BadDude("Bad", "Dude", number, 12);cout << "Draw time:" << badd->Gdraw() << endl;cout << "Next card:" << badd->Cdraw() << endl;delete badd;cout << "Bye.\n";return 0;
}
14-5
头文件和主函数都是和书上一样的
emp.h
#ifndef EMP_H_
#define EMP_H_#include <iostream>
#include <string>class abstr_emp
{
private:std::string fname;std::string lname;std::string job;
public:abstr_emp();abstr_emp(const std::string& fn, const std::string& ln, const std::string& j);virtual void ShowAll() const;virtual void SetAll();friend std::ostream& operator<<(std::ostream& os, const abstr_emp& e);virtual ~abstr_emp() = 0;
};class employee :public abstr_emp
{
public:employee();employee(const std::string& fn, const std::string& ln, const std::string& j);virtual void ShowAll() const;virtual void SetAll();
};class manager :virtual public abstr_emp
{
private:int inchargeof;
protected:void Data() const;void Get();int InChargeOf() const { return inchargeof; }int& InChargeOf() { return inchargeof; }
public:manager();manager(const std::string& fn, const std::string& ln, const std::string& j, int ico = 0);manager(const abstr_emp& e, int ico);manager(const manager& m);virtual void ShowAll() const;virtual void SetAll();
};class fink :virtual public abstr_emp
{
private:std::string reportsto;
protected:void Data() const;void Get();const std::string ReportsTo() const { return reportsto; }std::string& ReportsTo() { return reportsto; }
public:fink();fink(const std::string& fn, const std::string& ln, const std::string& j, const std::string& rpo);fink(const abstr_emp& e, const std::string& rpo);fink(const fink& e);virtual void ShowAll() const;virtual void SetAll();
};class highfink :public manager, public fink
{
public:highfink();highfink(const std::string& fn, const std::string& ln, const std::string& j, const std::string& rpo, int ico);highfink(const abstr_emp& e, const std::string& rpo, int ico);highfink(const fink& f, int ico);highfink(const manager& m, const std::string& rpo);highfink(const highfink& h);virtual void ShowAll() const;virtual void SetAll();
};#endif // !EMP_H_
emp.cpp
#include <iostream>
#include <string>
#include "emp.h"
using std::cout;
using std::cin;
using std::endl;abstr_emp::~abstr_emp() {}abstr_emp::abstr_emp()
{fname = "Null";lname = "Null";job = "Null";
}abstr_emp::abstr_emp(const std::string& fn, const std::string& ln, const std::string& j)
{fname = fn;lname = ln;job = j;
}void abstr_emp::ShowAll() const
{cout << "Fullname: " << fname << endl;cout << "Lastname: " << lname << endl;cout << "Job: " << job << endl;
}void abstr_emp::SetAll()
{cout << "Enter firstname: ";cin >> fname;cout << "Enter lastname: ";cin >> lname;cout << "Ente job: ";cin.get();getline(cin, job);
}std::ostream& operator<<(std::ostream& os, const abstr_emp& e)
{cout << e.fname << " " << e.lname << " " << e.job << endl;return os;// TODO: 在此处插入 return 语句
}employee::employee():abstr_emp()
{
}employee::employee(const std::string& fn, const std::string& ln, const std::string& j):abstr_emp(fn, ln, j)
{
}void employee::ShowAll() const
{abstr_emp::ShowAll();
}void employee::SetAll()
{abstr_emp::SetAll();
}void manager::Data() const
{cout << "Inchargeof: " << inchargeof << endl;
}void manager::Get()
{cout << "Enter Inchargeof: ";cin >> inchargeof;
}manager::manager():abstr_emp()
{inchargeof = 0;
}manager::manager(const std::string& fn, const std::string& ln, const std::string& j, int ico):abstr_emp(fn, ln, j)
{inchargeof = ico;
}manager::manager(const abstr_emp& e, int ico):abstr_emp(e), inchargeof(0)
{
}manager::manager(const manager& m):abstr_emp(m)
{inchargeof = m.inchargeof;
}void manager::ShowAll() const
{abstr_emp::ShowAll();cout << "Inchargeof: " << inchargeof << endl;
}void manager::SetAll()
{abstr_emp::SetAll();cout << "Enter inchargeof: ";cin >> inchargeof;
}void fink::Data() const
{cout << "Reportsto: " << reportsto << endl;
}void fink::Get()
{cout << "Enter resportsto: ";cin.get();getline(cin, reportsto);
}fink::fink():abstr_emp()
{reportsto = "Null";
}fink::fink(const std::string& fn, const std::string& ln, const std::string& j, const std::string& rpo):abstr_emp(fn, ln, j), reportsto(rpo)
{
}fink::fink(const abstr_emp& e, const std::string& rpo):abstr_emp(e), reportsto(rpo)
{
}fink::fink(const fink& e) : abstr_emp(e)
{reportsto = e.reportsto;
}void fink::ShowAll() const
{abstr_emp::ShowAll();cout << "Reports to: " << reportsto << endl;
}void fink::SetAll()
{abstr_emp::SetAll();cout << "Enter reports to: ";cin.get();getline(cin, reportsto);
}highfink::highfink():abstr_emp(), manager(),fink()
{
}highfink::highfink(const std::string& fn, const std::string& ln, const std::string& j, const std::string& rpo, int ico) :abstr_emp(fn, ln, j),manager(fn, ln, j, ico), fink(fn, ln, j, rpo)
{
}highfink::highfink(const abstr_emp& e, const std::string& rpo, int ico):abstr_emp(e), manager(e, ico), fink(e, rpo)
{
}highfink::highfink(const fink& f, int ico) : abstr_emp(f), manager(f, ico), fink(f)
{
}highfink::highfink(const manager& m, const std::string& rpo): abstr_emp(m), manager(m), fink(m, rpo)
{
}highfink::highfink(const highfink& h) : abstr_emp(h), manager(h), fink(h)
{
}void highfink::ShowAll() const
{abstr_emp::ShowAll();manager::Data();fink::Data();
}void highfink::SetAll()
{abstr_emp::SetAll();manager::Get();fink::Get();
}
main.cpp
#include <iostream>
using namespace std;
#include "emp.h"int main(void)
{employee em("Trip", "Harris", "Thumper");cout << em << endl;em.ShowAll();manager ma("Amorphia", "Spindragib", "Nuancer", 5);cout << ma << endl;ma.ShowAll();fink fi("Matt", "Oggs", "Oiler", "Juno Barr");cout << fi << endl;fi.ShowAll();highfink hf(ma, "Curly Kew");hf.ShowAll();cout << "Press a key for next phase:\n";cin.get();highfink hf2;hf2.SetAll();cout << "Using an abstr_emp * pointer:\n";abstr_emp* tri[4] = { &em,&fi,&hf,&hf2 };for (int i = 0; i < 4; i++)tri[i]->ShowAll();return 0;
}