必须写 operator+ 而不是普通函数,才能支持 a + b 语法及 std::accumulate 等模板依赖;它需为非成员友元函数以支持左操作数隐式转换,且返回值应为对象而非引用以启用移动语义。

什么时候必须写 operator+ 而不是用普通函数?
当你希望两个自定义对象能像 int 一样直接写 a + b,而不是调用 add(a, b) —— 这不只是语法糖,它影响接口一致性和模板推导。比如 std::accumulate 依赖 operator+,你若只提供普通函数,编译直接失败。
- 重载必须是类的成员函数或非成员友元函数;全局普通函数不被算作“运算符重载”
- 二元运算符如
operator+推荐用非成员函数实现(方便左操作数类型自动转换) - 如果类有隐式构造函数,
MyClass(5) + obj能工作;但若只写成员版obj.operator+(MyClass(5)),左边就不能是字面量或其它类型
operator= 的返回值和参数为什么必须是引用?
返回 MyClass& 是为了支持链式赋值 a = b = c;参数用 const MyClass& 是避免无谓拷贝,也防止误改右值。漏掉 & 会导致深拷贝爆炸,尤其对象含指针或大内存块时。
- 返回
void:链式赋值失效,(a = b) = c编译不过 - 参数用值传递:每次赋值都触发一次拷贝构造,性能雪崩
- 没写拷贝赋值运算符,编译器会生成默认版本——但默认版只做浅拷贝,指针成员会被双释放
重载 operator== 后,std::set 或 std::unordered_set 为什么还不认相等?
std::set 用 operator 判断顺序和唯一性,<code>std::unordered_set 需要单独提供哈希函数 std::hash<t></t> 和 operator==。只写 operator== 对两者都无效。
-
std::set<myclass></myclass>要求你定义operator(或传入比较函数),否则编译报错 <code>invalid operands to binary expression -
std::unordered_set<myclass></myclass>必须特化std::hash<myclass></myclass>,且确保operator==和哈希结果一致:相等对象必须有相同哈希值 - 别在
operator==里用memcmp直接比整个对象内存——有填充字节(padding)的话,结果不可靠
移动语义下,operator+ 怎么避免多余拷贝?
当右值参与运算(如临时对象、std::move(x)),应优先移动而非拷贝内部资源。典型做法是让 operator+ 返回值类型为 MyClass(非引用),再配合移动构造函数接管资源。
立即学习“C++免费学习笔记(深入)”;
- 不要在
operator+内部返回局部对象的引用——悬垂引用 - 确保类有移动构造函数和移动赋值运算符,否则即使写了
operator+,返回值仍会触发拷贝 - 如果
MyClass内部用std::vector<int></int>存数据,移动构造能瞬间转移指针,比拷贝快几个数量级
operator== 必须满足自反、对称、传递,operator 必须是严格弱序。这些约束不写在代码里,但违反了,容器和算法就会行为异常——而且往往不报错,只悄悄出错。










