C++运算符重载

本文详细介绍了C++中的运算符重载,包括类成员函数和友元函数的重载方式,以及特殊运算符如流、自增自减、文本运算符的重载。此外,还展示了如何通过运算符重载封装新的整数类型,并通过实例演示了Array类和myvector类的实现,以及Function类和Auto_ptr类中运算符的运用。
摘要由CSDN通过智能技术生成

目录

一、初识运算符重载

二、友元函数和类成员函数重载运算符

三、特殊运算符重载

        1.流运算符重载

        2.++ --运算符重载

        3.文本重载 (新标准中的,稍微落后一点开发工具不适用)

        4.其他运算符

        5.对象隐式转换                 

四、重载综合案例(简单封装一个新的int类型)

五、实战

        ● 封装一个Array类,实现定长数组的操作


一、初识运算符重载

        1.定义:赋予运算符具有操作自定义类型数据的功能

        2.实质:函数调用

        3.写法:函数返回值 函数名(函数参数)

                ● 函数返回值:运算完成后的值决定  ---->Complex

                ● 函    数   名:operator 加上重载运算符组成函数名----->operator+

                ● 参           数:看运算符的操作数,具体参数个数要看重载函数形式

                ● 函    数   体:写运算符具体想要的操作

二、友元函数和类成员函数重载运算符

#include<iostream>
#include<string>
using namespace std;
class Complex
{
public:
	//缺省写法
	Complex(int a = 0, int b = 0) :a(a), b(b){}
	//友元函数运算符重载 --->参数个数就是操作数据
	friend Complex operator+(Complex one, Complex two);
	//类成员函数重载,参数个数等于操作减一
	Complex operator-(Complex object)
	{
		return Complex(this->a - object.a, this->b - object.b);
	}
	void print()
	{
		cout << this->a << "\t" << this->b << endl;
	}
protected:
	int a;
	int b;
};
//友元函数运算符重载 --->参数个数就是操作数据
Complex operator+(Complex one, Complex two)
{
	return Complex(one.a + two.a, one.b + two.b);
}
int main()
{
	Complex one(1, 2);
	Complex two(2, 3);
	//隐式调用
	Complex three = one + two;//不做运算符重载无法相加
	cout << "one:" << endl;
	one.print();			//1 2
	cout << "two:" << endl;
	two.print();			//2 3
	cout << "three:" << endl;
	three.print();			//3 5
	//显式调用
	Complex four = one.operator-(two);
	cout << "four:" << endl;
	four.print();			//-1 -1
	while (1);
	return 0;
}

三、特殊运算符重载

        1.流运算符重载

                ● cin类型:istream类的对象

                ● cout类型:ostream类的对象

                ● 流运算符 >> <<

        注:必须采用友元函数形式重载

#include<iostream>
#include<string>
using namespace std;
class Person
{
public:
	Person(string name="", int age=18): name(name), age(age){}
	//重载流运算符
	friend istream& operator>>(istream& in, Person& mm);
	friend ostream& operator<<(ostream& out, Person& mm);
protected:
	string name;
	int age;
};
istream& operator>>(istream& in, Person& mm)
{
	in >> mm.name >> mm.age;
	return in;
}
ostream& operator<<(ostream& out, Person& mm)
{
	out << mm.name << "\t" << mm.age << endl;
	return out;
}
int main()
{
	Person mm("Miss Du", 19);
	Person gg("Mr Y", 20);
	cout << mm << endl;
	//因为需要连续输入输出,因此重载运算符应该返回输入输出流
	//istream& operator>>(istream& in, Person& mm);
	//ostream& operator<<(ostream& out, Person& mm);
	cout << mm << endl << gg << endl;
	while (1);
	return 0;
}

        2.++ --运算符重载

                需解决的问题:前置和后置---->通过增加无用参数 int去表示当前运算符重载是后置操作

#include<iostream>
#include<string>
using namespace std;
class Person
{
public:
	Person(string name = "", int age = 18) : name(name), age(age){}
	//重载流运算符
	friend istream& operator>>(istream& in, Person& mm)
	{
		in >> mm.name >> mm.age;
		return in;
	}
	friend ostream& operator<<(ostream& out, Person& mm)
	{
		out << mm.name << "\t" << mm.age << endl;
		return out;
	}
	Person operator++(int)//int无用参数,充当标记,表示后置运算
	{
		/*int num = age;
		age++;
		return MM(name, num);*/
		//上面三行等效下面一行
		return Person(name, age++);
	}
	Person operator++()//表示前置运算
	{
		return Person(name, ++age);
	}
protected:
	string name;
	int age;
};
int main()
{
	Person mm("Miss Du", 19);
	cout << mm << endl;
	Person mm2 = mm++;//mm2.age=19, mm.age=20;
	//上面等同于下面
	//Person mm2 = mm.operator++(1);
	cout << mm2 << endl;
	Person mm3 = mm.operator++();//等同于Person mm3=++mm;
	cout << mm3 << endl;//mm3.age=21;
	while (1);
	return 0;
}

        3.文本重载 (新标准中的,稍微落后一点开发工具不适用)

#include <iostream>
#include <string>
#include <chrono>
#include <thread>
using namespace std;
//文本重载
unsigned long long  operator"" _h(unsigned long long num) 
{
	return 60 * 60*num;
}
unsigned long long  operator"" _min(unsigned long long num)
{
	return 60 * num;
}
int main()
{
    //this_thread::sleep_for(3s);
	cout << "3s结束" << endl;

	int second = 1_h;
	cout << second << "s" << endl;

	int sum = 1_h + 18_min + 30;
	cout << sum << "s" << endl;
    while(1);
    return 0;
}

        4.其他运算符

                ● = () -> [] 只能采用类的成员函数形式重载

                ● 流重载采用友元方式

                ● .  .*  ?:   :: 不能重载

        5.对象隐式转换                 

#include<iostream>
#include<string>
using namespace std;
class Person
{
public:
	Person(string name = "", int age = 18) : name(name), age(age){}
	//类的对象的隐式转换  operator
	operator int()
	{
		return age;
	}
protected:
	string name;
	int age;
};
int main()
{

	Person girl("Miss Du", 19);
	int girlAge = girl;
	cout << girlAge << endl;
	while (1);
	return 0;
}

四、重载综合案例(简单封装一个新的int类型)

#include<iostream>
#include<string>
using namespace std;
class Int
{
public:
	Int(int num) :num(num){}
	int& data()//引用
	{
		return num;
	}
	Int operator+(const Int& value)//加法
	{
		return Int(this->num + value.num);
	}
	//友元重载 :操作数-1 等于重载函数的参数个数
	friend Int operator-(const Int& one,const Int&two)//减法
	{
		return Int(one.num - two.num);
	}
	//+=
	Int operator+=(const int& object)//引用数据
	{
		return Int(this->num + object);
	}
	Int operator+=(const Int& object)//Int对象
	{
		return Int(this->num + object.num);
	}
	//++ --
	Int operator++(int)
	{
		return Int(this->num++);
	}
	Int operator--()
	{
		return Int(--this->num);
	}
	//&运算
	Int operator&(const Int& value)
	{
		return Int(this->num&value.num);
	}
	//取反
	bool operator!()
	{
		return !this->num;
	}
	//负数
	Int operator-()
	{
		return Int(-this->num);
	}
	//流重载
	friend ostream& operator<<(ostream& out, const Int& object)
	{
		out << object.num << endl;
		return out;
	}
	friend  istream& operator>>(istream& in, Int& object)
	{
		in >> object.num;
		return in;
	}
	//指针
	int* operator&()
	{
		return &this->num;
	}
	//判断大小
	bool operator>(const Int& object)
	{
		return this->num > object.num;
	}
protected:
	int num;
};

//重载[]
class myvector
{
public:
	myvector(int size)
	{
		base = new int[size]{0};
	}
	int& operator[](int index)
	{
		return base[index];
	}
protected:
	int* base;
};
//重载()
class Function
{
	typedef void(*PF)();
public:
	Function(PF pf) :pf(pf) {}
	void operator()()
	{
		pf();
	}
protected:
	PF pf;
};
void print()
{
	cout << "测试函数" << endl;
}
int sum(int a, int b)
{
	return a + b;
}
//->
struct MM
{
	string name;
	int age;
	MM(string name, int age) :name(name), age(age) {}
};
class Auto_ptr
{
public:
	Auto_ptr(int* ptr) :ptr(ptr) {}
	Auto_ptr(MM* ptr) :ptrMM(ptr) {}
	int& operator*()
	{
		return *ptr;
	}
	MM* operator->()
	{
		return ptrMM;
	}
	//手动写析构函数
	~Auto_ptr()
	{
		if (ptr)
		{
			delete ptr;
			ptr = nullptr;
		}
		if (ptrMM)
		{
			delete ptrMM;
			ptrMM = nullptr;
		}
	}
protected:
	int* ptr;
	MM* ptrMM;
};
void testAuto_ptr()
{
	Auto_ptr ptr(new int(18));
	cout << *ptr << endl;
	Auto_ptr ptrMM(new MM("mm", 19));
	cout << ptrMM->name << endl;
	cout << ptrMM->age << endl;
	//先了解 需加 #include <memory>头文件
	/*auto_ptr<int> autoPtr(new int(18));
	cout << *autoPtr << endl;
	auto_ptr<MM> autoPtrMM(new MM("mm", 19));
	cout << autoPtrMM->name << endl;
	cout << autoPtrMM->age << endl;*/
}
int main()
{
	Int num(10);
	cout << num << endl;
	cout << -num << endl;
	myvector vec(5);
	for (int i = 0; i < 5; i++)
	{
		cin >> vec[i];
	}
	for (int i = 0; i < 5; i++)
	{
		cout << vec[i]<<" ";
	}
	Function p(print);
	p();
	//了解--->需加#include <functional>
	//function<int(int,int)> pf(max);
	//cout << pf(1, 2) << endl;
	testAuto_ptr();
	while (1);
	return 0;
}

五、实战

        ● 封装一个Array类,实现定长数组的操作

//以下测试代码要能够成功运行
Array array(4);
for(int i=0;i<array.size();i++)
{
    cin>>array[i];
}
for(int i=0;i<array.size();i++)
{
    cout<<array[i];
}
//实现数组的连接
Array one(3);   //输入1 2 3 
cin>>one;
Array two(4);   //输入2 3 4
cin>>two;
Array  sum=one+two;
cout<<sum<<endl;  //打印1 2 3 2 3 4
Array num;
num=sum;
cout<<num<<endl;

#include<iostream>
#include<string>
using namespace std;
class MyArray
{
public:
	MyArray() = default;
	MyArray(int size)
	{
		this->size = size;
		base = new int[this->size];
	}
	int getSize()
	{
		return this->size;
	}
	int& operator[](int index)
	{
		return base[index];
	}
	friend ostream& operator<<(ostream& out, MyArray& object)
	{
		for (int i = 0; i < object.size; i++)
		{
			out << object.base[i];
		}
		return out;
	}
	friend  istream& operator>>(istream& in, MyArray& object)
	{
		for (int i = 0; i < object.size; i++)
		{
			in >> object.base[i];
		}
		return in;
	}
	MyArray operator+(MyArray& object)
	{
		MyArray* temp = new MyArray(this->getSize() + object.getSize());
		int j = 0;
		for (int i = 0; i < this->size; i++)
		{
			temp->base[j++] = this->base[i];
		}
		for (int i = 0; i < object.size; i++)
		{
			temp->base[j++] = object.base[i];
		}
		return *temp;
	}
	MyArray(MyArray& object)
	{
		this->size = object.size;
		this->base = new int[this->size];
		for (int i = 0; i < this->size; i++)
		{
			this->base[i] = object.base[i];
		}
	}
	~MyArray()
	{
		delete[]base;
	}
protected:
	int size;
	int* base;
};
int main()
{
	//以下测试代码要能够成功运行
	MyArray array(4);
	for (int i = 0; i<array.getSize(); i++)
	{
		cin >> array[i];
	}
	for (int i = 0; i<array.getSize(); i++)
	{
		cout << array[i];
	}
	cout << endl;
	//实现数组的连接
	MyArray one(3);
	cin >> one;
	MyArray two(4);
	cin >> two;
	MyArray sum = one + two;
	cout << sum << endl; 
	MyArray num;
	num = sum;
	cout << num << endl;
	while (1);
	return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值