练习14.1:
区别:一些运算符的重载版本无法保留内置运算符的短路求值属性,或者无法保留内置运算符的求值顺序规则。重载的运算符函数至少含有一个类类型的参数
一致:重载运算符函数的参数数量与该运算符内置版本作用的运算对象一样多。对于一个重载的运算符来说,其优先级和结合律与对应的内置运算符保持一致
练习14.2:
#include <iostream>
#include <string>
#include <errno.h>
using namespace std;
class Sales_date {
//将非成员重载函数设置为友元函数
friend Sales_date operator+(const Sales_date& h1, const Sales_date& h2);
friend istream& operator >> (istream& is, Sales_date& item);
friend ostream& operator << (ostream& os, const Sales_date& item);
public:
//默认构造函数
Sales_date():bookNo(std::string()){ }
Sales_date(const std::string& s, unsigned us, double p):bookNo(s), units_sold(us), revenue(p*us) { }
Sales_date(const std::string& s) :bookNo(s) { }
//拷贝构造函数
Sales_date(const Sales_date& s):bookNo(s.bookNo), units_sold(s.units_sold), revenue(s.revenue){ }
//拷贝赋值运算符
Sales_date& operator=(const Sales_date&);
//复合赋值运算符
Sales_date& operator+=(const Sales_date&);
//得到bookNo
std::string isbn()const { return bookNo; }
private:
//平均售价
double avg_price()const { return units_sold ? revenue / units_sold : 0; }
std::string bookNo;
unsigned units_sold = 0;
double revenue = 0.0;
};
//拷贝赋值运算符
Sales_date& Sales_date::operator=(const Sales_date& s)
{
bookNo = s.bookNo;
units_sold = s.units_sold;
revenue = s.revenue;
return *this;
}
//复合赋值运算符
Sales_date& Sales_date::operator+=(const Sales_date& s)
{
if (this->bookNo == s.bookNo)
{
units_sold = units_sold + s.units_sold;
revenue = revenue + s.revenue;
return *this;
}
else
{
throw runtime_error("bookNo is different");
}
}
//重载的加法运算符
Sales_date operator+(const Sales_date& h1, const Sales_date& h2)
{
if (h1.bookNo == h2.bookNo)
{
Sales_date sTemp = h1;
sTemp.units_sold = sTemp.units_sold + h2.units_sold;
sTemp.revenue = sTemp.revenue + h2.revenue;
return sTemp;
}
else
{
//无法相加
throw runtime_error("bookNo is different");
}
}
//重载输入运算符
istream& operator >> (istream& is, Sales_date& item)
{
double price;
is >> item.bookNo >> item.units_sold >> price;
//检查输入是否出错
if (is)
{
item.revenue = item.units_sold * price;
}
else
{
//输入失败,对象被赋予默认的状态
item = Sales_date();
}
return is;
}
//重载输出运算符
ostream& operator << (ostream& os, const Sales_date& item)
{
os << item.isbn() << " " << item.units_sold << " " << item.revenue << " " << item.avg_price();
return os;
}
int main()
{
system("pause");
return 0;
}
练习14.3:
(a):内置类型的==运算符,比较两个指针指向的内容
(b):string版本重载的==
(c):vector版本重载的==
(d):此处书上左边的变量多了一个”,去除,使用的是string版本重载的==,右边的字面值字符串被转换为string类型
练习14.4:
%一般定义为非成员函数
%=改变对象状态,一般定义为成员函数
++会改变对象状态,一般定义为成员函数
->必须定义为成员函数
<<必须定义为非成员函数
&&是对称性的运算符,一般定义为非成员函数
==是对称性的运算符,一般定义为非成员函数
()必须定义为成员函数
练习14.5:
略,与Sales_Date的重载运算符的编写一样