15.3 Quote销售书籍基类
#ifndef QUOTE_H
#define QUOTE_H
#include <string>
#include <iostream>
#include <vector>
using namespace std;
class Quote
{
public:
Quote() = default;
Quote(string const &b, double p) : bookNo(b), price(p) {}
string isbn() const { return bookNo; }
virtual double net_price(size_t n) const { return n * price; }
virtual void debug() const;
virtual ~Quote() = default;
private:
string bookNo;
protected:
double price = 0.0;
};
void Quote::debug() const
{
std::cout << "data members of this class:\n"
<< "bookNo= " <<this->bookNo << " "
<< "price= " <<this->price<< " ";
}
#endif
15.5 Bulk_quote派生类-打折销售
#ifndef BULK_QUOTE_H
#define BULK_QUOTE_H
#include <string>
#include <iostream>
#include <vector>
#include <quote.h>
using namespace std;
class Bulk_quote : public Quote
{
public:
Bulk_quote() = default;
Bulk_quote(string const &b, double p, size_t q, double disc) : Quote(b, p), min_qty(q), discount(disc) {}
double net_price(size_t n) const override;
void debug() const override;
private:
size_t min_qty = 0;
double discount = 0.0;
};
double Bulk_quote::net_price(size_t n) const
{
return n * price * ( n >= min_qty ? 1-discount : 1);
}
void Bulk_quote::debug() const
{
Quote::debug();
std::cout << "min_qty= " << this->min_qty << " "
<< "discount= " << this->discount<< " ";
}
#endif
15.15 定义支持不同折扣策略的通用Disc_quote抽象基类和某种特定策略的Bulk_quote类
#ifndef DISC_QUOTE_H
#define DISC_QUOTE_H
using namespace std;
#include "quote.h"
class Disc_quote : public Quote
{
public:
Disc_quote();
Disc_quote(const string &b, double p, size_t q, double d) : Quote(b, p), quantity(q), discount(d) { }
virtual double net_price(size_t n) const override = 0;
protected:
size_t quantity;
double discount;
};
#endif
#ifndef BULK_QUOTE_H
#define BULK_QUOTE_H
#include <string>
#include <iostream>
#include <vector>
#include <disc_quote.h>
using namespace std;
class Bulk_quote : public Disc_quote
{
public:
Bulk_quote() = default;
Bulk_quote(string const &b, double p, size_t q, double disc) : Disc_quote(b, p, q, disc) {}
double net_price(size_t n) const override;
void debug() const override;
};
double Bulk_quote::net_price(size_t n) const
{
return n * price * ( n >= quantity ? 1-discount : 1);
}
void Bulk_quote::debug() const
{
Quote::debug();
std::cout
<< "min_qty= " << quantity << " "
<< "discount= " << discount<< " ";
}
#endif
15.21-22 图形继承体系
#include <utility>
#include <string>
using namespace std;
class Shape
{
public:
typedef pair<double, double> Coordinate;
Shape() = default;
Shape(const string& n) : name(n) { }
virtual double area() const = 0;
virtual double perimeter() const = 0;
virtual ~Shape() = default;
private:
string name;
};
class Rectangle : public Shape
{
public:
Rectangle() = default;
Rectangle(const std::string& n,
const Coordinate& a, const Coordinate& b,
const Coordinate& c, const Coordinate& d) :
Shape(n), a(a), b(b), c(c), d(d) { }
~Rectangle() = default;
protected:
Coordinate a;
Coordinate b;
Coordinate c;
Coordinate d;
};
class Square : public Rectangle
{
public:
Square() = default;
Square(const std::string& n,
const Coordinate& a, const Coordinate& b,
const Coordinate& c, const Coordinate& d) :
Rectangle(n, a, b, c, d) { }
~Square() = default;
};
15.28-29 定义一个存放Quote对象的vector,将Bulk_qoute传入其中,计算vector中所有元素总的net_price。在运行一次,这次传入Quote对象的shared_ptr。
#include <vector>
#include <iostream>
#include <algorithm>
#include "Quote.h"
using namespace std;
int main(int argc, char**argv)
{
vector<Quote> vec1;
bulk_quote b1(string("C++ Primer I"),128,10,0.5);
bulk_quote b2(string("C++ Primer II"),118,8,0.6);
bulk_quote b3(string("C++ Primer III"),108,12,0.4);
bulk_quote b4(string("C++ Primer IV"),138,4,0.3);
vec1.push_back(b1);
vec1.push_back(b2);
vec1.push_back(b3);
vec1.push_back(b4);
double Sum_of_net_price1 = 0;
for(int i = 0; i < vec1.size(); ++i)
{
Sum_of_net_price1 += vec1[i].net_price(20);
cout<<Sum_of_net_price1<<endl;
}
cout<<"The total net price is:"<<Sum_of_net_price1<<endl;
vector<shared_ptr<Quote>> vec2;
vec2.push_back(make_shared<bulk_quote>(b1));
vec2.push_back(make_shared<bulk_quote>(b2));
vec2.push_back(make_shared<bulk_quote>(b3));
vec2.push_back(make_shared<bulk_quote>(b4));
double Sum_of_net_price2 = 0;
for(int i = 0; i < vec2.size(); ++i)
{
Sum_of_net_price2 += vec2[i]->net_price(20);
cout<<Sum_of_net_price2<<endl;
}
cout<<"The total net price is:"<<Sum_of_net_price2<<endl;
return 0;
}
15.30 编写Basket类,计算交易记录的总价格
#ifndef BASKET_H
#define BASKET_H
#include "quote.h"
#include "bulk_quote.h"
using namespace std;
class Basket
{
public:
Basket() = default;
void add_item(const Quote &sale) { items.insert(shared_ptr<Quote>(sale.clone())); }
void add_item(Quote &&sale) { items.insert(shared_ptr<Quote>(std::move(sale).clone())); }
inline double total_receipt(std::ostream&) const;
private:
static bool compare(const shared_ptr<Quote> &lhs, const shared_ptr<Quote> &rhs)
{
return lhs->isbn() < rhs->isbn();
}
};
inline double Basket::total_receipt(std::ostream &os) const
{
auto sum = 0.0;
for (auto iter = items.cbegin(); iter != items.cend(); iter = items.upper_bound(*iter))
{
sum += print_total(os, **iter, items.count(*iter));
}
os << "Total Sale: " << sum << std::endl;
return sum;
}
#endif
15.35 实现Query类和Query_base类,其中需要定义rep而无须定义eval
#ifndef QUERY_H
#define QUERY_H
#include <string>
#include <vector>
#include <set>
#include <map>
using namespace std;
class TextQuery;
class QueryResult
{
public:
typedef vector<string>::size_type line_no;
friend ostream& operator<<(ostream&, const QueryResult&);
public:
QueryResult(const string& s, shared_ptr<std::set<line_no>> set,shared_ptr<vector<string>> v)
: word(s), nos(set), input(v) { }
private:
string word;
shared_ptr<std::set<line_no>> nos;
shared_ptr<vector<string>> input;
};
class TextQuery
{
public:
typedef vector<string>::size_type line_no;
TextQuery(ifstream&);
QueryResult query(const string&) const;
private:
shared_ptr<vector<string>> input;
map<string, shared_ptr<set<line_no>>> result;
};
class Query_base
{
friend class Query;
private:
virtual string rep() const = 0;
protected:
typedef vector<string>::size_type line_no;
virtual ~Query_base() ;
};
class Query
{
friend Query operator~(const Query&);
friend Query operator|(const Query&,const Query&);
friend Query operator&(const Query&,const Query&);
public:
Query(const string&s);
string rep() const
{
return q->rep();
}
private:
Query(shared_ptr<Query_base> query):q(query){}
shared_ptr<Query_base> q;
};
std::ostream &operator<<(std::ostream &os, const Query query)
{
return os << query.rep();
}
class WordQuery:public Query_base
{
friend class Query;
WordQuery(const string &s):Query_word(s){cout<<"WordQuery"<<endl;}
QueryResult eval(const TextQuery& t) const
{
return t.query(Query_word);
}
string rep() const
{
return Query_word;
}
string Query_word;
};
inline Query::Query(const string &s):q(new WordQuery(s)){cout<<"Query"<<endl;}
class NotQuery:public Query_base
{
friend Query operator~(const Query&);
NotQuery(const Query&q):query(q){cout<<"NotQuery"<<endl;}
string rep()
{
return "~("+query.rep()+")";
}
QueryResult eval(const TextQuery&);
Query query;
};
class BinaryQuery:public Query_base
{
protected:
BinaryQuery(const Query&l, const Query&r,string s):lhs(l),rhs(r),opSym(s){cout<<"BinaryQuery"<<endl;}
string rep() const
{ cout<<"Binary_rep"<<endl;
return "("+lhs.rep()+" "+opSym+" "+rhs.rep()+")";
}
Query lhs,rhs;
string opSym;
};
class AndQuery:public BinaryQuery
{
protected:
friend Query operator&(const Query&,const Query&);
AndQuery(const Query&left, const Query&right):BinaryQuery(left,right,"&"){cout<<"AndQuery"<<endl;}
QueryResult eval(const TextQuery&);
};
class OrQuery:public BinaryQuery
{
protected:
friend Query operator|(const Query&,const Query&);
OrQuery(const Query&left, const Query&right):BinaryQuery(left,right,"|"){cout<<"OrQuery"<<endl;}
QueryResult eval(const TextQuery&);
};
#endif QUERY_H