当前位置: 首页 > news >正文

C++类基础(十一)

运算符重载(二)
● 对称运算符通常定义为非成员函数以支持首个操作数的类型转换

struct Str
{int val = 0;Str(int input): val(input){}auto operator+(Str x){std::cout << "auto operator+(Str x)\n";return Str(val + x.val);}
};
int main()
{Str x = 3;Str z = x + 4; //通过类Str的构造函数将4转换为Str类型与x相加Str u = 4 + x; //Error: Invalid operands to binary expression ('int' and 'Str')return 0;
}

在这里插入图片描述

struct Str
{int val = 0;Str(int input): val(input){}
};
auto operator+(Str input1, Str input2)
{std::cout << "auto operator+(Str input1, Str input2)\n";return Str(input1.val + input2.val);
}
int main()
{Str x = 3;Str y = x + 3; OKreturn 0;
}
struct Str
{Str(int input): val(input){}friend auto operator+(Str, Str);
private:int val = 0;
};
auto operator+(Str input1, Str input2)
{std::cout << "auto operator+(Str input1, Str input2)\n";return Str(input1.val + input2.val);
}
int main()
{Str x = 3;Str y = x + 3;Str z = 3 + y;return 0;
}

● 移位运算符一定要定义为非成员函数,因为其首个操作数类型为流类型

struct Str
{Str(int input): val(input){}friend auto operator+(Str input1, Str input2){return Str(input1.val + input2.val);}friend auto& operator<<(std::ostream& output, Str input) //返回引用,第一个参数类型是std::ostream{output << input.val;return output;}
private:int val = 0;
};
int main()
{Str x = 3;Str y = x + 3;std::cout << x << ' ' << y <<std::endl;return 0;
}

在这里插入图片描述

● 赋值运算符也可以接收一般参数

struct Str
{Str(): val(0){}Str(int input): val(input){}Str& operator=(const Str& input) //重载赋值运算符1。重载运算符只接受一个参数,因为缺省参数是*this。{val = input.val;return *this;}Str& operator=(const std::string& input) //重载赋值运算符2{val = static_cast<int>(input.size());return *this;}
//private:int val;
};
int main()
{Str x = 3;//Str y = "12345"; //调用构造函数而非重载赋值运算符Str y;y = "12345"; //调用重载赋值运算符std::cout << y.val << std::endl;return 0;
}

在这里插入图片描述

● operator [] 通常返回引用

struct Str
{Str(): val(0){}Str(int input): val(input){}Str& operator=(const Str& input) //重载赋值运算符1,{val = input.val;return *this;}Str& operator=(const std::string& input) //重载赋值运算符2{val = static_cast<int>(input.size());return *this;}//int operator[](int id) //返回“值”,只读,不可执行写操作int& operator[](int id) //#1返回引用,可读可写,但是*this可被修改{return val;}int operator[](int id) const //#2const修饰构成重载返回“值”,可读不可写,即*this不可被修改{return val;}
//private:int val;
};
int main()
{Str x = 3;x = "12345";std::cout << x[0] << '\n'; //读x[0] = 100; //写std::cout << x[0] << '\n';const Str cx = 3;//std::cout << cx[0] << std::endl; //见#1,Error: No viable overloaded operator[] for type 'const Str'std::cout << cx[0] << std::endl; //OK,见#2return 0;
}

在这里插入图片描述

● 自增、自减运算符的前缀、后缀重载方法

struct Str
{Str(): val(0){}Str(int input): val(input){}//Str operator++() //返回“值”,Error: cannot increment value of type 'void'Str& operator++() //前缀自增{++val;return *this;}Str operator++(int) //后缀自增,返回“值”{Str tmp(*this); //调用拷贝构造,构造临时对象,编译器不一定能优化,导致性能上的损失++val;return tmp;}
//private:int val;
};
int main()
{Str s;++(++s); //调用前缀自增std::cout << s.val <<std::endl;std::cout << (s++).val << std::endl; //调用后缀自增std::cout << s.val <<std::endl;return 0;
}

在这里插入图片描述

● 使用解引用运算符( * )与成员访问运算符( -> )模拟指针行为
– 注意“ .” 运算符不能重载

通过类对象而不是指向类对象的指针调用其成员的,所以不能重载

struct Str
{Str(int* p): ptr(p){}//operator*() //Error: C++ requires a type specifier for all declarationsint& operator*() //返回引用,支持读写操作{return *ptr;}int operator*() const //返回“值”,只读{return *ptr;}
private:int* ptr;
};
int main()
{int x = 100;Str ptr(&x);std::cout << *ptr << std::endl; //读*ptr = 101; //写std::cout << *ptr << std::endl;return 0;
}

在这里插入图片描述

– “→” 会递归调用 操作 “→”

struct Str
{Str(int* p): ptr(p){}Str* operator ->() //重载运算符本质上是个函数{return this;}int val = 5;
private:int* ptr;
};
int main()
{int x = 100;Str ptr(&x);std::cout << ptr->val << std::endl; //#1std::cout << (ptr.operator->()->val) << std::endl; //#2 #1与#2等价return 0;
}

在这里插入图片描述

struct Str2
{Str2* operator->(){return this;}int blabla = 20;
};struct Str
{Str(int* p): ptr(p){}Str2 operator ->() //类Str中重载->运算符返回Str2类对象{return Str2{};}int val = 5;
private:int* ptr;
};
int main()
{int x = 100;Str ptr(&x);std::cout << ptr->blabla << std::endl; //#1std::cout << (ptr.operator->().operator->()->blabla) << std::endl; //#2 #1与#2等价return 0;
}

在这里插入图片描述

int operator->() //Error: member type 'int' is not a pointer
{return blabla;
}int* operator->() //Error: member reference base type 'int' is not a structure or a union
{return &blabla;
}

● 使用函数调用运算符构造可调用对象

struct Str
{Str(int p): val(p){}int operator()(){return val;}int operator()(int x, int y, int z) //参数列表不同,重载{return val + x + y +z;}
private:int val;
};
int main()
{ Str obj(100);std::cout << obj() << std::endl;std::cout << obj(1, 2, 3) << std::endl;return 0;
}

在这里插入图片描述

struct Str
{Str(int p): val(p){}int& operator()(){return this->val;}bool operator()(int input) //参数依据实际情况修改,更加灵活,是Lambda表达式的基础{//return val < input;return val++ < input;}
private:int val;
};
int main()
{ Str obj(100);std::cout << obj() << std::endl;std::cout << obj(1) << std::endl;std::cout << obj() << std::endl;std::cout << obj(199) << std::endl;std::cout << obj() << std::endl;return 0;
}

在这里插入图片描述

参考
深蓝学院:C++基础与深度解析

http://www.lryc.cn/news/4138.html

相关文章:

  • Windows安装系列:SVN Server服务
  • 快速傅里叶算法(FFT)快在哪里?
  • 利用Markdown写学术论文资料汇总贴
  • MySQL 高级查询
  • JavaSE学习day4_01 循环for,while,do...while
  • C/C++中的static关键字
  • 67 自注意力【动手学深度学习v2】
  • 电子学会2022年12月青少年软件编程(图形化)等级考试试卷(二级)答案解析
  • 关于链表中插入结点的操作……
  • 【项目精选】百货中心供应链管理系统
  • Qt优秀开源项目之十六:SQLite数据库管理系统—SQLiteStudio
  • Python __doc__属性:查看文档
  • 电子科技大学操作系统期末复习笔记(一):操作系统概述
  • [实践篇]13.20 Qnx进程管理slm学习笔记(三)
  • 冰冰学习笔记:多线程
  • 补充一些前端面试题
  • 七大设计原则之单一职责原则应用
  • [USACO23JAN] Leaders B
  • C++模板初阶
  • 文献阅读:Scaling Instruction-Finetuned Language Models
  • gpt草稿
  • mysal第三次作业
  • 分页和mmap
  • C++之异常处理
  • 牛客寒假集训营6 E 阿宁的生成树
  • 嵌入式C基础知识(10)
  • TC3xx FlexRay™ 协议控制器 (E-Ray)-01
  • 优劣解距离法TOPSIS——清风老师
  • 【Unity3D】Shader常量、变量、结构体、函数
  • LeetCode 刷题系列 -- 496. 下一个更大元素 I