排序和建堆的使用方式(自定義為例)
在C++中,排序和建堆的比較規(guī)則是通過比較函數(shù)或者比較對(duì)象來定義的。這通常涉及到使用函數(shù)對(duì)象(Functor)或者函數(shù)指針,以決定元素之間的大小關(guān)系。
舉例: 利用函數(shù)排序
#include <iostream>
#include <vector>
#include <algorithm>
// 自定義比較函數(shù)
bool myComparator(int a, int b) {
return a > b; // 降序排序
}
int main() {
std::vector<int> vec = {5, 2, 8, 1, 6};
// 使用自定義比較函數(shù)進(jìn)行降序排序
std::sort(vec.begin(), vec.end(), myComparator);
// 輸出排序后的結(jié)果
for (int num : vec) {
std::cout << num << " ";
}
return 0;
}
舉例: 利用對(duì)象排序,注意sort第三個(gè)實(shí)參中有括號(hào),是建立臨時(shí)對(duì)象
#include <iostream>
#include <vector>
#include <algorithm>
// 自定義比較對(duì)象
struct MyComparator {
bool operator()(int a, int b) {
return a > b; // 降序排序
}
};
int main() {
std::vector<int> vec = {5, 2, 8, 1, 6};
// 使用自定義比較對(duì)象進(jìn)行降序排序
std::sort(vec.begin(), vec.end(), MyComparator());
// 輸出排序后的結(jié)果
for (int num : vec) {
std::cout << num << " ";
}
return 0;
}
舉例: 利用對(duì)象建堆,注意優(yōu)先級(jí)隊(duì)列(本例中為小頂堆)第三個(gè)模板參數(shù)不帶括號(hào)
#include <iostream>
#include <queue>
// 自定義比較對(duì)象
struct MyComparator {
bool operator()(int a, int b) {
return a > b; // 小頂堆,小的元素排在前面
}
};
int main() {
std::priority_queue<int, std::vector<int>, MyComparator> minHeap;
// 插入元素
minHeap.push(5);
minHeap.push(2);
minHeap.push(8);
minHeap.push(1);
minHeap.push(6);
// 彈出并輸出元素
while (!minHeap.empty()) {
std::cout << minHeap.top() << " ";
minHeap.pop();
}
return 0;
}
結(jié)論
如果是排序,less<T>是升序,(從左到右遍歷下標(biāo),數(shù)組元素從小到大);greater<T>是降序(從左到右遍歷下標(biāo),元素從大到?。?。
如果是建堆,less<T>是大頂堆,greater<T>是小頂堆。
less()、greater()原理
假設(shè)比較規(guī)則就是comp(a, b),對(duì)于排序來說,左邊元素就是前一個(gè)a,右邊元素就是后一個(gè)b;對(duì)于建堆,新插入一個(gè)元素時(shí),插入到最后一個(gè)葉子,這時(shí)要整理堆內(nèi)元素滿足大/小頂堆,a代表新插入的結(jié)點(diǎn),b代表它的父節(jié)點(diǎn)。
我們寫自定義比較規(guī)則就可以依照這個(gè)規(guī)則。
而標(biāo)準(zhǔn)庫中的less<T>就是讓a比b小,對(duì)應(yīng)排序就是左邊比右邊小,就是升序;對(duì)于建堆就是讓新插入節(jié)點(diǎn)比它的父結(jié)點(diǎn)小,就是大頂堆。
greater<T>相反。
默認(rèn)都是用less<T>。
自定義規(guī)則
這部分參考里的例子寫的很好,直接貼過來了。
符合兩個(gè)條件:
bool:返回值bool
return x<y;:重載<之類的操作符,并且要決定比較什么元素。
PS:建議還要常引用,保險(xiǎn),禁止發(fā)生修改要比較的元素可能。
舉例:數(shù)組
函數(shù):使用時(shí)不加括號(hào),加了報(bào)錯(cuò)
類的對(duì)象:注意,排序時(shí)的類必須使用類的對(duì)象才對(duì),直接使用類報(bào)錯(cuò)。
#include <iostream>
#include <algorithm>
#include <vector>
using namespace std;
// 重寫排序函數(shù)
bool cmpfunc(const int &a, const int &b)
{
return a < b;
// < 升序; > 降序
}
// 模仿less、greater構(gòu)建類
struct cmpClass
{
bool operator()(const int &i, const int &j)
{
return (i < j);
}
}cmpClassObject; // 注意,排序時(shí)的類必須使用類的對(duì)象才對(duì),使用類報(bào)錯(cuò)。
int main()
{
// 使用函數(shù)
vector<int> v1 = {2, 3, 1, 6, 2, 5, 4};
// 使用時(shí)不加括號(hào),加了報(bào)錯(cuò)
sort(v1.begin(), v1.end(), cmpfunc);
for (int i = 0; i < v1.size(); i++)
{
cout << v1[i] << " ";
}
cout << endl;
// 1 2 2 3 4 5 6
// 使用類的對(duì)象
vector<int> v2 = {2, 3, 1, 6, 2, 5, 4};
sort(v2.begin(), v2.end(), cmpClassObject);
for (int i = 0; i < v2.size(); i++)
{
cout << v2[i] << " ";
}
cout << endl;
// 1 2 2 3 4 5 6
return 0;
}
舉例:優(yōu)先級(jí)隊(duì)列
定義類時(shí)同時(shí)定義操作符重載函數(shù):操作符重載函數(shù),必須是具體的操作符<之類的,寫()報(bào)錯(cuò)
自定義類,自定義比較函數(shù):操作符重載函數(shù),必須是具體的操作符<之類的,寫()報(bào)錯(cuò)
自定義類,自定義包含比較函數(shù)的結(jié)構(gòu)體:操作符重載函數(shù),必須是寫()文章來源:http://www.zghlxwxcb.cn/news/detail-809680.html
#include <iostream>
#include <queue>
using namespace std;
/******** 定義類時(shí)同時(shí)定義操作符重載函數(shù) ********/
struct Node1
{
// 要比較的元素
int x;
// 構(gòu)造函數(shù)
Node1(int x) { this->x = x; }
// 操作符重載函數(shù),必須是具體的操作符<之類的,寫()報(bào)錯(cuò)
bool operator<(const Node1 &b) const
{
// 實(shí)現(xiàn)less中需要的<,大頂堆
return x < b.x;
}
};
/******** 自定義類,自定義比較函數(shù) ********/
struct Node2
{
// 要比較的元素
int x;
// 構(gòu)造函數(shù)
Node2(int x) { this->x = x; }
};
// 操作符重載函數(shù),必須是具體的操作符<之類的,寫()報(bào)錯(cuò)
bool operator<(const Node2 &a, const Node2 &b)
{
// less,大頂堆
return a.x < b.x;
}
/******** 自定義類,自定義包含比較函數(shù)的結(jié)構(gòu)體 ********/
struct Node3
{
// 要比較的元素
int x;
// 構(gòu)造函數(shù)
Node3(int x) { this->x = x; }
};
struct cmpClass
{
// 操作符重載函數(shù),必須是寫()
bool operator()(const Node3 &a, const Node3 &b)
{
// less,大頂堆
return a.x < b.x;
}
};
int main()
{
/******** 初始化優(yōu)先級(jí)隊(duì)列的對(duì)象p ********/
// Node1類型,默認(rèn)使用vector,小頂堆,同 priority_queue<Node1, vector<Node1>, less<Node1> > p;
priority_queue<Node1> p;
// 亂序入隊(duì)
p.emplace(1);
p.emplace(3);
p.emplace(2);
// 彈出隊(duì)首
while (!p.empty())
{
cout << p.top().x << " ";
p.pop();
}
cout << endl;
// 3 2 1
/******** 初始化優(yōu)先級(jí)隊(duì)列的對(duì)象q ********/
// 同 priority_queue<Node2> q;
priority_queue<Node2, vector<Node2>, less<Node2>> q;
// 亂序入隊(duì)
q.emplace(1);
q.emplace(3);
q.emplace(2);
// 彈出隊(duì)首
while (!q.empty())
{
cout << q.top().x << " ";
q.pop();
}
cout << endl;
// 3 2 1
/******** 初始化優(yōu)先級(jí)隊(duì)列的對(duì)象r ********/
priority_queue<Node3, vector<Node3>, cmpClass> r;
// 亂序入隊(duì)
r.emplace(1);
r.emplace(3);
r.emplace(2);
// 彈出隊(duì)首
while (!r.empty())
{
cout << r.top().x << " ";
r.pop();
}
cout << endl;
// 3 2 1
return 0;
}
參考:
C++:std::greater()、std::less()、自定義比較函數(shù)的規(guī)則
C++ std::優(yōu)先級(jí)隊(duì)列priority_queue文章來源地址http://www.zghlxwxcb.cn/news/detail-809680.html
到了這里,關(guān)于關(guān)于C++中排序和建堆的比較規(guī)則:std::greater()、std::less()、自定義比較規(guī)則的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!