十五. C++运算符重载

目录

运算符重载概念

语法:

重载+友元

常用运算符重载

加号运算符重载

前置后置自增(++)运算符重载

前置++运算符重载

后置++运算符重载

左移运算符(<<)重载

指针运算符重载

赋值运算符重载

关系运算符重载

函数调用运算符重载


运算符重载概念

在c++中,可以定义一个处理类的新运算符。这种定义很像一个普通的函数定义,只是函数的名字由关键字operator及其紧跟的运算符组成。差别仅此而已。它像任何其他函数一样也是一个函数,当编译器遇到适当的模式时,就会调用这个函数。

语法:

定义重载的运算符就像定义函数,只是该函数的名字是operator@,这里的@代表了被重载的运算符。函数的参数中参数个数取决于两个因素。

  • 运算符是一元(一个参数)的还是二元(两个参数)
  • 运算符被定义为全局函数还是成员函数

重载+友元

友元函数是一个全局函数,和我们上例写的全局函数类似,只是友元函数可以访问某个类私有数据。

常用运算符重载

加号运算符重载

代码实例:

#define _CRI_SCREURE_NO_WARNINGS
#define _CRT_SCREURE_NO_WARNINGS
#include<iostream>
#include<string>
using namespace std;

class Person
{
public:
	Person() {};
	Person(int a, int b) :m_A(a), m_B(b)
	{
	}
	//+号运算符重载 成员函数
	//Person operator+(Person &p)
	//{
	//	Person tmp;
	//	tmp.m_A = this->m_A + p.m_A;
	//	tmp.m_B = this->m_B + p.m_B;
	//	return tmp;
	//}
	int m_A;
	int m_B;
};

//利用全局函数 进行+号运算符重载
Person operator+(Person& p1, Person& p2)  //二元
{
	Person tmp;
	tmp.m_A = p1.m_A + p2.m_B;
	tmp.m_B = p1.m_A + p2.m_B;
	return tmp;
}

Person operator+(Person& p1, int a)  //重载的版本
{
	Person tmp;
	tmp.m_A = p1.m_A + a;
	tmp.m_B = p1.m_A + a;
	return tmp;
}

void test01()
{
	Person p1(10, 10);
	Person p2(10, 10);
	Person p3 = p1 + p2;  //没有与这些操作匹配的运算符
	Person p4 = p1 + 7;
	cout << "p3的m_A:" << p3.m_A << endl;
	cout << "p4的m_A:" << p4.m_A << endl;
}
int main()
{
	test01();
	return 0;
}

前置后置自增(++)运算符重载

前置++运算符重载

#define _CRI_SCREURE_NO_WARNINGS
#define _CRT_SCREURE_NO_WARNINGS
#include<iostream>
#include<string>
using namespace std;

class MyInteger
{
	friend ostream& operator<<(ostream& cout, MyInteger& myInt);
public:
	MyInteger()   //构造函数
	{
		m_Num = 2;
	}
	//前置++重载
	MyInteger& operator++()
	{
		this->m_Num++;
		return *this;
	}
	int m_Num;
};

ostream& operator<< (ostream& cout, MyInteger& myInt)
{//左移运算符重载
	cout << myInt.m_Num;
	return cout;
}

void test01()
{
	MyInteger myInt;
	cout << ++myInt << endl;
}
int main()
{
	test01();
	return 0;
}

后置++运算符重载

#define _CRI_SCREURE_NO_WARNINGS
#define _CRT_SCREURE_NO_WARNINGS
#include<iostream>
#include<string>
using namespace std;

class MyInteger
{
	friend ostream& operator<<(ostream& cout, MyInteger& myInt);
public:
	MyInteger()   //构造函数
	{
		m_Num = 2;
	}
	//后置++重载
	MyInteger operator++(int)
	{
		//先保存目前的数据
		MyInteger tmp = *this;
		m_Num++;
		return tmp;
	}
	int m_Num;
};

ostream& operator<< (ostream& cout, MyInteger& myInt)
{//左移运算符重载
	cout << myInt.m_Num;
	return cout;
}

void test01()
{
	MyInteger myInt;
	myInt++;
	cout << myInt << endl;
}
int main()
{
	test01();
	return 0;
}

左移运算符(<<)重载

#define _CRI_SCREURE_NO_WARNINGS
#define _CRT_SCREURE_NO_WARNINGS
#include<iostream>
#include<string>
using namespace std;

class Person
{
	friend ostream& operator<< (ostream& cout, Person& p1);
public:
	Person() {}
	Person(int a, int b)
	{
		this->m_A = a;
		this->m_B = b;
	}
private:
	int m_A;
	int m_B;
};

ostream& operator<< (ostream& cout,Person& p1)
{//第一个参数cout 第二个参数p1
	cout << "m_A=" << p1.m_A <<" "<<"m_B=" << p1.m_B << endl;
	return cout;   //cout为引用类型
}

void test01()
{
	Person p1(10, 10);
	cout << p1<<endl;
}

int main()
{
	test01();
	return 0;
}

指针运算符重载

#define _CRI_SCREURE_NO_WARNINGS
#define _CRT_SCREURE_NO_WARNINGS
#include<iostream>
#include<string>
using namespace std;

class Person
{
public:
	Person(int age)
	{
		this->m_Age = age;
	}

	void showAge()
	{
		cout << "年龄为" << this->m_Age << endl;

	}
	~Person()
	{
		cout << "析构调用" << endl;
	}
	int m_Age;
};

//智能指针
//用来托管自定义类型的对象,让对象进行自动的释放
class smartPointer
{
public:
	smartPointer(Person* person)
	{
		this->person = person;
	}
	//重载->让智能指针对象像Person *p一样去使用
	Person* operator->()
	{
		return this->person;
	}
	//重载* 
	Person& operator*()
	{
		return *this->person;
	}
	~smartPointer()
	{
		cout << "智能指针析构" << endl;
		if (this->person != NULL)
		{
			delete this->person;
			this->person = NULL;
		}
	}
private:
	Person* person;
};

void test01()
{
//	Person p1(10);
//	Person* p1 = new Person(10);
//	delete p1;
	smartPointer sp(new Person(10));   //sp开辟到了栈上
	sp->showAge(); //sp->->showAge(); 编译器优化了
	(*sp).showAge();
}

int main()
{
	test01();
	return 0;
}

赋值运算符重载

#define _CRI_SECURE_NO_WARNINGS
#define _CRT_SECURE_NO_WARNINGS
#include<iostream>
#include<string>
using namespace std;

//一个类默认创建 默认构造、析构、拷贝  operator=赋值运算符(进行简单的值传递)
class Person
{
public:
	Person(int a)
	{
		this->m_A = a;
	}
	int m_A;
};

void test01()
{
	Person p1(10);
	Person p2(0);
	p2 = p1;   //赋值
	cout << "p2的m_A" << p2.m_A << endl;
}

class Person2
{
public:
	Person2(const char* name)
	{
		this->pName=new char[strlen(name)+1];
		strcpy(this->pName, name);
	}

	//重载=赋值运算符
	Person2& operator=(const Person2 &p)
	{
		//判断如果原来堆区有内容,先释放
		if (this->pName != NULL)
		{
			delete[] this->pName;
			this->pName = NULL;
		}
		this->pName = new char[strlen(p.pName) + 1];
		strcpy(this->pName, p.pName);
		return *this;
	}
	~Person2()
	{
		if (this->pName != NULL)
		{
			cout << "析构函数调用" << endl;
			delete[] this->pName;
			this->pName = NULL;
		}
	}
	char* pName;
};

void test02()
{
	Person2 p1("goudan");
	Person2 p2("gousheng");
	Person2 p3("gou");
	p3 = p2 = p1;
	p2 = p1;
	cout << p2.pName << endl;
}
int main()
{
	test02();
	return 0;
}

关系运算符重载

#define _CRI_SECURE_NO_WARNINGS
#define _CRT_SECURE_NO_WARNINGS
using namespace std;
#include<iostream>
#include<string>

//  ==
class Person
{
public:
	Person(string name, int age)
	{
		this->m_Name = name;
		this->m_Age = m_Age;
	}

	bool operator==(Person &p)
	{
		if (this->m_Name == p.m_Name && this->m_Age == p.m_Age)
		{
			return true;
		}
		return false;
	}

public:
	string m_Name;
	int m_Age;
};
void test01()
{
	Person p1("小米", 10);
	Person p2("xiaoqiang", 15);
	Person p3("xiaoqiang", 15);

	if (p2 == p3)
	{
		cout << "p1和p2相等" << endl;
	}
	else
	{
		cout << "p1和p2不相等" << endl;
	}
}

int main()
{
	test01();
	return 0;
}

函数调用运算符重载

#define _CRI_SECURE_NO_WARNINGS
#define _CRT_SECURE_NO_WARNINGS
using namespace std;
#include<iostream>
#include<string>

//()重载
class MyPrint
{
public:
	void operator()(string text)
	{
		cout << text << endl;
	}
};
void test01()
{
	MyPrint myPrint;
	myPrint("hello world");     //仿函数
}

class MyAdd
{
public:
	int operator()(int v1, int v2)
	{
		return v1 + v2;
	}
};

void test02()
{
	MyAdd myAdd;
//	cout << myAdd(1, 1) << endl;
	cout << MyAdd()(1, 1) << endl;  //匿名对象
}

int main()
{
	test02();
	return 0;
}

 

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值