c++之说_9_6|自定义类型 struct operator 重载运算符关键字

c++中 struct  和 class  特性几乎一模一样

所以很多都是共有的特性 篇幅就很多了

c++中  我觉得最牛皮的概念之一 就是

重载运算符  operator 关键字

这个东西 能将  我们的  运算符 (+-*/) new  delete

 类型转换

写在类里面当成员函数 并制定 该类型变量运算时所适用的逻辑

以下是可重载的所有运算符:

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第1张图片

 这是重载运算符时的方式 注意  运算符替换掉 @

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第2张图片

 运算符 前缀后缀 放置位

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第3张图片

 限制 或 不可重载的符号

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第4张图片


struct obj_3
{

	obj_3() {};
	obj_3(const int& Ina, const int& Inb) : a(Ina), b(Inb) {}


	int	geta()const { return a; };

	int	getb()const { return b; };


private:

	int a = 0;
	int b = 0;

};


struct obj_1
{

public:
	obj_1() { Ts = this;  };
	//使用了委托构造
	obj_1(const int& Ina, const int& Inb) : obj_1() { a = Ina; b = Inb; }


	int	geta() const { return a; };

	int	getb() const { return b; };
public:

	bool operator== (const obj_1& Target)
	{
		
		return  (this->a == Target.a) && (this->b == Target.b);
	};

	bool operator!= (const obj_1& Target)
	{

		return  !operator==(Target);
	};
	operator obj_3()
	{
		std::cout << __func__ << ":" << endl;
		return obj_3(99, 99);
	}

	void* operator new(std::size_t size, void* p, int io,char* c)
	{
		std::cout << "obj_1::" << __func__ << "(std::size_t size, void* p,char* c) :" << endl;
		std::cout << "operator new 构造的地址是:" << p << endl;
		std::cout << "operator new   io :" << io << endl;
		std::cout << "operator new   c :" << c << endl;
		return p;
	}

	void operator delete(void* p,size_t size, const char* c)
	{
		std::cout << "obj_1::" << __func__ << "(void* p,size_t size, const char* c) :" << endl;
		std::cout << "operator delete的地址是:" << p << endl;
		std::cout << "operator delete   size :" << size << endl;
		std::cout << "operator delete   c :" << c << endl;
		return;

	}


	int	operator[](int i)
	{
		std::cout << "obj_1::" << __func__ << "(int i) :" << endl;
		std::cout << "i = "<< i << endl;
		return a + i;
	}

	~obj_1() {};


private:

	obj_1* Ts;

	int a = 0;
	int b = 0;

};

struct obj_2
{

	obj_2() {};
	obj_2(const int& Ina, const int& Inb) : a(Ina), b(Inb) {}


	int	geta()const { return a; };

	int	getb()const { return b; };

	obj_2& operator= (const obj_1& Target)
	{

		std::cout << "obj_2::" << __func__ << "(const obj_1& Target) :" << endl;

		this->a = Target.geta();
		this->b = Target.getb();

		return *this;
	};

	operator obj_1()
	{

		std::cout << "obj_2::" << __func__ << ":" << endl;
		return	obj_1(this->a, 100);
	}


	~obj_2() {};


private:

	int a = 0;
	int b = 0;

};


int main()
{
	std::cout << __func__ <<":"<< endl;

	obj_1 a1(10, 1000);
	obj_2 b2(50, 10);
	obj_3 c3;
	obj_1 texta1;
	obj_2 textb2;


	std::cout << "初始化完各个对象的值" << endl;
	std::cout << "a1.a: "<

部分测试代码我已放上

接下来我们运行看看

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第5张图片

好 我们先看看第一处

textb2 =    a1;

textb2 是obj_2类型  a1 是obj_1类型

本来两个互不相同的自定义类型是无法使用 = 运算符的

但是此刻可以了 为何讷 

就因为运算符重载 operator

我们找到 obj_2 结构体是如何定义的

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第6张图片

我们发现 有个 

obj_2& operator= (const obj_1& Target) 函数

其中有个输出函数 我们继续来看控制台

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第7张图片

 obj_2::operator =(const obj_1& Target) :

证明  textb2 =    a1;

的确是运行了此函数

所以  obj_2& operator= (const obj_1& Target)

这个叫什么?

这个叫重载赋值符号

Target引用的值其实就是  a1

这是类中的写法

具体详细的大家去打断点试试

------------------------------------------------------------------------------

接下来看看这个

texta1 = (obj_1)b2;

texta1 是obj_1类型  b2 是obj_2类型

这语句一看 类型转换

但是细看  不对劲  不相关类型 如何支持转换

看了下控制台  输出了obj_2::operator struct obj_1:

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第8张图片

我们去找找 obj_2里  输出的地方

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第9张图片

operator obj_1()

这是什么?

这叫类型转换函数

obj_2 里面有个这个  证明了 有转换到 obj_1类型的方法

它返回了一个obj_1的临时对象  

我们看看a 和 b

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第10张图片

  b2.a: 50
     b2.b: 10

  texta1.a: 50
     texta1.b: 100

构造的临时对象中的a使用了 b2.a , b使用了 100 

看了  没错是正确的

还是不太懂?

没事 继续看看 

    c3 = a1; 

 obj_3类型 c3    obj_1类型 a1;

这题一看 哎呦  我会 刚刚学过的  重载赋值运算符嘛!

一看输出  不对劲   operator struct obj_3:

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第11张图片

怎么是类型转换函数呢?

去 obj_3类中看看

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第12张图片

发现并没有operator 的函数

那就去obj_1类中看看

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第13张图片

operator obj_3()

发现了obj_3 类型转换函数

所以这题运行的是类型转换函数

--------------------------------------------------------------------

接下来我们看

 a1[100]  

这个不是数组写法吗?

a1不是 obj_1类型的对象吗?

如何能当数组用  它又输出何物?

我们去看看obj_1类中怎么写的

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第14张图片

我们发现了   int    operator[](int i)

看见了什么 operator 关键字  又是重载运算符

这次原来是重载数组运算符

返回的是 return a + i;

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第15张图片

看了下 输出是 110 

之前a1.a 是多少?

-----------------------------------------------------------------

接下来我们来看看

void* operator new

重载 new 与 delete

直呼woc  c++ 还有什么运算符不能重载

void* operator new(std::size_t size, void* p, int io,char* c)

当然重载new 有一定的要求:

第一个形参必须是 size_t 类型的参数

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第16张图片

看编译报错了

一般何时我们需要重载new呢?

要在指定的空间上进行创建对象时会进行重载

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第17张图片

比如这里

我们看到了一个 
    obj_1* pobjw = new(b, 9000,&p) obj_1;

这写法很怪异

我们注意到了

b 是一个数组变量  证明是个地址

new(b, 9000,&p)  而语句是如此

我们去看看 重载位置 obj_1类中

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第18张图片

看到了形参顺序 std::size_t size, void* p, int io,char* c

而调用是 new(b, 9000,&p) obj_1

有输出语句 我们去看看

我们发现 b= 00007FF6B74C0E90  io = 9000    c = ’2‘

顺序是按照  new(b, 9000,&p) obj_1

至于delete 要求是 第一个形参必须为  void *

还有一件事

可以加 virtual 关键字  也就是说可以成为虚函数  当然new 的例外  这个是 static 修饰的

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第19张图片

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第20张图片

c++之说_9_6|自定义类型 struct operator 重载运算符关键字_第21张图片

我们可以看到虚表是被子类的 operator+(int c) 所覆盖了的 尽管她俩 返回值类型不同

浅谈结束

大家可以去该网站看看特性 语法规则

https://zh.cppreference.com/w/cpp/language/operators

你可能感兴趣的:(c++,开发语言)