重载操作符
- 首先 c++ 重载操作符只能在 class 或者结构体中
- 以下面的代码为例
#include <bits/stdc++.h> using namespace std; using ll = long long; const int N = 2e5 + 9; struct Book { int a, b, c; bool operator<(const Book &x) const { if (a != x.a) return a < x.a; if (b != x.b) return b < x.b; return c < x.c; } } p[N]; int main() { ios::sync_with_stdio(0), cin.tie(0), cout.tie(0); int n; cin >> n; for (int i = 1; i <= n; ++i) cin >> p[i].a >> p[i].b >> p[i].c; sort(p + 1, p + n + 1); for (int i = 1; i <= n; ++i) cout << p[i].a << " " << p[i].b << " " << p[i].c << "\n"; return 0; }
在这段代码中,定义了一个
Book
结构体,其中包含三个整数类型的成员变量a
、b
和c
。重点在于对<
运算符的重载,这是在 C++中自定义类型排序逻辑的一种常见做法。通过重载<
运算符,我们可以使Book
类型的对象能够使用标准库函数std::sort
进行排序。
对 <
运算符的重载
bool operator<(const Book &x) const { if (a != x.a) return a < x.a; if (b != x.b) return b < x.b; return c < x.c; }
对代码的解释
这段代码重载了 <
运算符,使得两个 Book
对象可以直接比较。这里的比较逻辑是:
-
首先比较
a
字段:如果当前对象的a
字段不等于另一个对象的a
字段,则比较这两个a
字段的大小。如果当前对象的a
小于另一个对象的a
,则返回true
,表示当前对象应排在另一个对象之前;否则,返回false
。 -
然后比较
b
字段:如果a
字段相等,接下来比较b
字段。逻辑与比较a
字段相同。 -
最后比较
c
字段:如果a
和b
字段都相等,最后比较c
字段,逻辑也相同。
主函数 main
在 main
函数中,首先通过 ios::sync_with_stdio(0), cin.tie(0), cout.tie(0);
禁用 C 和 C++标准库之间的同步,从而加速输入输出操作。
接着,读入整数 n
,表示 Book
对象的数量。通过一个循环,读取每个 Book
对象的 a
、b
、c
字段值。
使用 std::sort
函数,按照重载的 <
运算符定义的逻辑,对数组 p
中从索引 1
到 n
(包含)的 Book
对象进行排序。
最后,通过另一个循环,按排序后的顺序输出每个 Book
对象的 a
、b
、c
字段。
总结
通过重载 <
运算符,该代码实现了 Book
结构体对象的自定义排序逻辑。这种方法使得 Book
对象可以直接使用 std::sort
等标准库算法进行排序,提供了一种灵活且强大的方式来定义对象间的排序规则。
这一行代码 bool operator<(const Book &x) const
是在 C++中对 <
操作符进行重载的声明,具体到 Book
结构体的上下文中。这个操作符重载使得可以直接比较两个 Book
类型的对象。下面详细解释这段代码的各个部分:
详细解释 bool operator<(const Book &x) const,以及为什么能在结构体内对操作符进行重载,vector 是否可以完成
解释
-
bool
:这是函数的返回类型,表示该操作符重载函数返回一个布尔值,用于指示调用对象是否小于传入的参数对象。 -
operator<
:这指明正在被重载的是<
操作符。 -
(const Book &x)
:这是函数的参数列表,表示该函数接受一个类型为const Book&
的参数。const
保证传入的对象x
不会在函数中被修改,&
表示传递的是对象的引用,避免了对象的拷贝,提高了效率。 -
const
(在参数列表后):这个const
表示该成员函数不会修改调用它的对象的状态。这是常量成员函数的标记,确保了在该函数内部不能修改任何成员变量(除了那些被声明为mutable
的成员变量)。
为什么能在结构体内对操作符进行重载?
在 C++中,结构体(struct
)与类(class
)非常相似,唯一的区别是默认的访问权限:struct
的成员默认是公开的(public
),而 class
的成员默认是私有的(private
)。因此,你可以在结构体内部定义成员函数,包括操作符重载函数,就像在类中一样。这提供了一种定义如何通过标准操作符对自定义类型进行操作的方式,使得自定义类型的使用更加直观和自然。
vector
可以完成操作符重载吗?
std::vector
是 C++标准模板库(STL)的一部分,它是一个模板类,不是用户定义的类型,因此你不能为 std::vector
直接添加操作符重载。操作符重载需要在类或结构体的定义内部进行。然而,你可以对存储在 vector
中的自定义类型(如 Book
)进行操作符重载,就像上面的例子那样。然后,你可以利用这些重载来对 vector<Book>
进行排序等操作,因为 std::sort
等函数会使用这些重载来比较 vector
中的元素。
总之,操作符重载在结构体或类内部定义,使得这些自定义类型可以以一种直观和自然的方式使用操作符。虽然不能直接为 std::vector
这样的模板类重载操作符,但可以通过重载存储在其中的自定义类型的操作符来实现间接的效果。
参数是如何被调用
在 C++中,当对操作符进行重载并使用这个重载操作符比较两个对象时,参数的调用遵循特定的规则。以 bool operator<(const Book &x) const
为例,这里解释如何调用这个重载的 <
操作符以及参数是如何被传递的。
操作符重载函数的调用
假设有两个 Book
类型的对象:book1
和 book2
。当你使用 book1 < book2
这样的表达式时,这实际上是在调用 book1
的 operator<
函数,并将 book2
作为参数传递给这个函数。
Book book1, book2; // 假设book1和book2已经被适当初始化 if (book1 < book2) { // 逻辑处理 }
这个表达式等价于直接调用:
if (book1.operator<(book2)) { // 逻辑处理 }
参数的传递
-
对象
book1
:作为比较操作的调用方,book1
的状态不会被修改,因为operator<
被声明为const
。这意味着在该函数内部不能修改book1
的任何成员变量。 -
对象
book2
:作为参数传递给operator<
函数。通过使用const Book &x
作为参数类型,book2
是以引用的方式传递的,同时保证了在operator<
函数内部不会修改book2
。使用引用传递避免了不必要的对象拷贝,提高了效率。同时,const
修饰符确保了函数内部不能修改传入对象的状态,这是一种良好的实践,可以保护函数外部的数据不被意外修改。
总结
在 C++中,当你对重载的操作符进行调用时,调用对象作为操作符函数的隐式调用方(相当于函数的 this
指针指向的对象),而其他参数则根据操作符函数的声明被显式传递。通过这种方式,C++允许开发者定义类型如何响应标准操作符,既保持了代码的直观性,又提供了强大的自定义能力。
在提供的代码片段中,<
操作符被重载用于 Book
结构体,使得 Book
对象可以被直接比较。这个重载的操作符实际上被使用在 main
函数中的 sort
函数调用里:
sort(p + 1, p + n + 1);
这行代码使用 std::sort
来对 Book
类型的数组 p
进行排序,范围从 p[1]
到 p[n]
(注意 C++中数组默认是从0开始索引的,但这里从1开始使用,可能是基于特定的需求或习惯)。std::sort
函数内部会多次比较数组中的元素来确定它们的排序顺序。当 std::sort
需要比较两个 Book
对象时(例如,决定哪个对象应该排在前面),它就会调用我们重载的 <
操作符。
这种比较逻辑允许 std::sort
根据 Book
对象的 a
、b
和 c
成员变量的值来排序这些对象。具体的比较逻辑首先比较 a
值,如果 a
值相同,则比较 b
值,如果 b
值也相同,则最后比较 c
值。这样,std::sort
可以根据重载的 <
操作符正确地排序 Book
数组。
总结
<
操作符的重载在 Book
对象数组的排序中发挥了作用,即在 std::sort
函数内部被隐式调用以确定数组中元素的顺序。这展示了操作符重载在自定义类型排序中的强大能力,使得自定义类型可以像内置类型那样,通过标准库算法进行有效的排序和比较。
本文作者:Phantasia1116
本文链接:https://www.cnblogs.com/Phantasia/p/18057650
版权声明:本作品采用知识共享署名-非商业性使用-禁止演绎 2.5 中国大陆许可协议进行许可。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步