std::priority_queue (C++98) là container adapter cài đặt max-heap mặc định (phần tử lớn nhất ở top). Để dùng với struct/class, cần cung cấp comparator (hàm so sánh).
Cấu trúc comparator
Comparator là functor (struct có operator()) hoặc lambda (C++11) trả về true nếu a có ưu tiên thấp hơn b (để max-heap: a < b).
Ví dụ: Priority Queue cho struct Student
#include <iostream>
#include <queue>
#include <vector>
using namespace std;
struct Student {
int roll, marks;
Student(int r, int m) : roll(r), marks(m) {}
};
// Comparator: ưu tiên marks CAO hơn -> top là marks lớn nhất
// priority_queue dùng less mặc định -> top là MAX.
// Với custom comparator: trả về true nếu a kém hơn b (a "nhỏ hơn" b).
struct CompareMarks {
bool operator()(const Student& a, const Student& b) const {
return a.marks < b.marks; // a kém hơn b khi marks nhỏ hơn -> max-heap theo marks
}
};
int main() {
// Cú pháp đầy đủ: priority_queue
priority_queue<Student, vector<Student>, CompareMarks> pq;
int data[6][2] = {{15,50}, {16,60}, {18,70}, {14,80}, {12,90}, {20,100}};
for (auto& d : data) pq.emplace(d[0], d[1]);
cout << "Priority queue (max marks first):\n";
while (!pq.empty()) {
Student s = pq.top(); pq.pop();
cout << s.roll << ' ' << s.marks << '\n';
}
return 0;
}
Kết quả
Priority queue (max marks first): 20 100 12 90 14 80 18 70 16 60 15 50
Giải thích comparator
| Mục tiêu | Comparator trả về true khi | Kết quả top() |
|---|---|---|
| Max-heap (mặc định less) | a < b | Phần tử LỚN NHẤT |
| Min-heap | a > b | Phần tử NHỎ NHẤT |
| Max theo marks | a.marks < b.marks | Marks LỚN NHẤT |
| Min theo marks | a.marks > b.marks | Marks NHỎ NHẤT |
Mẹo nhớ: Comparator giống như std::less cho max-heap. priority_queue đặt phần tử "lớn nhất" theo comparator lên top.
Dùng Lambda (C++11)
auto cmp = [](const Student& a, const Student& b) { return a.marks < b.marks; };
priority_queue<Student, vector<Student>, decltype(cmp)> pq(cmp);
Lưu ý quan trọng
- Comparator phải là Strict Weak Ordering (bán thứ tự chặt).
- Struct/class nên có constructor, hoặc dùng
emplace. - Không thể duyệt priority_queue (không có iterator) – chỉ
top(),pop(),push(). - Cần duyệt sorted → đổ ra vector rồi sort, hoặc dùng
std::multiset.
Ứng dụng thực tế
- Thuật toán Dijkstra, A* (min-heap distance).
- Huffman coding (min-heap frequency).
- Task scheduling (priority-based).
- K largest/smallest elements (streaming).