C++基礎(chǔ)知識(shí)之運(yùn)算符重載詳解
運(yùn)算符重載
- 為什么要使用運(yùn)算符重載
-C/C++的運(yùn)算符,支持的數(shù)據(jù)類型,僅限于基本數(shù)據(jù)類型。
- 問題:一頭牛+一頭馬 = ?(牛馬神獸?)
一個(gè)圓 +一個(gè)圓 = ? (想要變成一個(gè)更大的圓)
一頭牛 – 一只羊 = ? (想要變成4只羊,原始的以物易物:1頭牛價(jià)值5只羊)
- 解決方案:
使用運(yùn)算符重載
方式一, 使用成員函數(shù)重載運(yùn)算符 需求:把牛肉換豬肉, 羊肉換豬肉
規(guī)則:
一斤牛肉:2斤豬肉
一斤羊肉:3斤豬肉
實(shí)現(xiàn):
牛 + 牛 = ?豬肉
牛 + 羊 = ?豬肉
Cow類
> Cow.h
#pragma once
class Pork;
class Sheep;
class Cow{ //牛類
public:
Cow(int weight = 0);
//使用運(yùn)算符重載, 實(shí)現(xiàn) 牛肉 + 牛肉 = 豬肉
Pork operator+(const Cow& cow);
//使用運(yùn)算符重載, 實(shí)現(xiàn) 牛肉 + 羊肉 = 豬肉
Pork operator+(const Sheep& sheep);
private:
int weight; //重量
};
_________________________________________________________________________________________________________________________________
> Cow.cpp
#include "Cow.h"
#include "Pork.h"
#include "Sheep.h"
Cow::Cow(int weight){
this->weight = weight;
}
//一斤牛肉換兩斤豬肉
Pork Cow::operator+(const Cow& cow){
return Pork((this->weight + cow.weight) * 2);
}
//一斤牛肉換兩斤豬肉, 一斤羊肉換三斤豬肉
Pork Cow::operator+(const Sheep& sheep){
int tmp = (this->weight * 2) + (sheep.getWeight() * 3);
return Pork(tmp);
}
Sheep類
> Sheep.h
#pragma once
//羊類
class Sheep{
public:
Sheep(int weight = 0);
int getWeight() const;
private:
int weight; //重量
};
_________________________________________________________________________________________________________________________________
> Sheep.cpp
#include "Sheep.h"
Sheep::Sheep(int weight){
this->weight = weight;
}
int Sheep::getWeight() const{
return weight;
}
Pork類
> Pork.h
#pragma once
#include <string>
using namespace std;
class Pork{ //豬肉類
public:
Pork(int weight = 0);
string description() const;
private:
int weight;
};
_________________________________________________________________________________________________________________________________
> Pork.cpp
#include <sstream>
#include "Pork.h"
Pork::Pork(int weight){
this->weight = weight;
}
string Pork::description() const{
stringstream ret;
ret << this->weight << "斤";
return ret.str();
}
main.cpp
#include <iostream>
#include <Windows.h>
#include "Cow.h"
#include "Pork.h"
#include "Sheep.h"
using namespace std;
int main(void) {
Pork p1;
Cow c1(100);
Cow c2(200);
Sheep s1(100);
//調(diào)用運(yùn)算符重載 Pork operator+(const Cow& cow);
p1 = c1 + c2;
cout << "牛 + 牛 = 豬肉:" << p1.description() << endl;
//調(diào)用運(yùn)算符重載 Pork operator+(const Sheep& c1);
p1 = c1 + s1;
cout << "牛 + 羊 = 豬肉:" << p1.description() << endl;
//羊+牛會(huì)報(bào)錯(cuò), 因?yàn)闆]有定義對應(yīng)的羊+牛運(yùn)算符重載
//p1 = s1 + c1;
system("pause");
return 0;
}
方式二, 使用非成員函數(shù)【友元函數(shù)】重載運(yùn)算符
實(shí)現(xiàn):
牛 + 牛 = ?豬肉
牛 + 羊 = ?豬肉
Cow類
> Cow.h
#pragma once
class Pork;
class Sheep;
class Cow{ //牛類
public:
Cow(int weight = 0);
//使用友元運(yùn)算符重載, 實(shí)現(xiàn) 牛肉 + 牛肉 = 豬肉
friend Pork operator+(const Cow& c1, const Cow& c2);
//使用友元運(yùn)算符重載, 實(shí)現(xiàn) 牛肉 + 羊肉 = 豬肉
friend Pork operator+(const Cow& c1, const Sheep& s1);
private:
int weight; //重量
};
_________________________________________________________________________________________________________________________________
> Cow.cpp
#include "Cow.h"
Cow::Cow(int weight){
this->weight = weight;
}
Sheep類
> Sheep.h
#pragma once
//羊類
class Sheep{
public:
Sheep(int weight = 0);
int getWeight() const;
private:
int weight; //重量
};
_________________________________________________________________________________________________________________________________
> Sheep.cpp
#include "Sheep.h"
Sheep::Sheep(int weight){
this->weight = weight;
}
int Sheep::getWeight() const{
return weight;
}
Pork類
> Pork.h
#pragma once
#include <string>
using namespace std;
class Pork{ //豬肉類
public:
Pork(int weight = 0);
string description() const;
private:
int weight;
};
_________________________________________________________________________________________________________________________________
> Pork.cpp
#include <sstream>
#include "Pork.h"
Pork::Pork(int weight){
this->weight = weight;
}
string Pork::description() const{
stringstream ret;
ret << this->weight << "斤";
return ret.str();
}
main.cpp
#include <iostream>
#include <Windows.h>
#include "Cow.h"
#include "Pork.h"
#include "Sheep.h"
using namespace std;
//要想訪問類的私有數(shù)據(jù)成員, 就把這個(gè)函數(shù)定義為友元
Pork operator+(const Cow& c1, const Cow& c2) {
return ((c1.weight + c2.weight) * 2);
}
//要想訪問類的私有數(shù)據(jù)成員, 就把這個(gè)函數(shù)定義為友元
Pork operator+(const Cow& c1, const Sheep& s1) {
return((c1.weight * 2) + (s1.getWeight() * 3));
}
int main(void) {
Pork p1;
Cow c1(100); //100斤的牛
Cow c2(200); //200斤的牛
Sheep s1(100); //100斤的羊
//調(diào)用 friend Pork operator+(const Cow& c1, const Cow& c2);
p1 = c1 + c2;
cout << "使用友元 牛 + 牛 = 豬肉:" << p1.description() << endl;
//調(diào)用 friend Pork operator+(const Cow& c1, const Sheep& s1);
p1 = c1 + s1;
cout << "使用友元 牛 + 羊 = 豬肉:" << p1.description() << endl;
system("pause");
return 0;
}
兩種方式的區(qū)別
區(qū)別:
使用成員函數(shù)來實(shí)現(xiàn)運(yùn)算符重載時(shí),少寫一個(gè)參數(shù),因?yàn)榈谝粋€(gè)參數(shù)就是this指針。
兩種方式的選擇:
- 一般情況下,單目運(yùn)算符重載,使用成員函數(shù)進(jìn)行重載更方便(不用寫參數(shù))
- 一般情況下,雙目運(yùn)算符重載,使用友元函數(shù)更直觀
方便實(shí)現(xiàn)a+b和b+a相同的效果,成員函數(shù)方式無法實(shí)現(xiàn)。
例如: 100 + cow; 只能通過友元函數(shù)來實(shí)現(xiàn)
cow +100; 友元函數(shù)和成員函數(shù)都可以實(shí)現(xiàn)
- 特殊情況:
(1)= () [ ] -> 不能重載為類的友元函數(shù)?。。。ǚ駝t可能和C++的其他規(guī)則矛盾),只能使用成員函數(shù)形式進(jìn)行重載。
(2)如果運(yùn)算符的第一個(gè)操作數(shù)要求使用隱式類型轉(zhuǎn)換,則必須為友元函數(shù)(成員函數(shù)方式的第一個(gè)參數(shù)是this指針)
注意:
同一個(gè)運(yùn)算符重載, 不能同時(shí)使用兩種方式來重載,會(huì)導(dǎo)致編譯器不知道選擇哪一個(gè)(二義性)
總結(jié)
本篇文章就到這里了,希望能夠給你帶來幫助,也希望您能夠多多關(guān)注腳本之家的更多內(nèi)容!
相關(guān)文章
C語言 動(dòng)態(tài)內(nèi)存分配的詳解及實(shí)例
這篇文章主要介紹了C語言 動(dòng)態(tài)內(nèi)存分配的詳解及實(shí)例的相關(guān)資料,需要的朋友可以參考下2016-09-09
帶你用C語言實(shí)現(xiàn)strtok和字符串分割函數(shù)
下面小編就為大家?guī)硪黄猚語言中字符串分割函數(shù)及實(shí)現(xiàn)方法。小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2021-09-09

