Bruce Eckel's Thinking in C++, 2nd Ed | Contents | Prev | Next |
//: C20:PriorityQueue1.cpp #include <iostream> #include <queue> #include <cstdlib> #include <ctime> using namespace std; int main() { priority_queue<int> pqi; srand(time(0)); // Seed random number generator for(int i = 0; i < 100; i++) pqi.push(rand() % 25); while(!pqi.empty()) { cout << pqi.top() << ' '; pqi.pop(); } } ///:~
//: C20:PriorityQueue2.cpp // Changing the priority #include <iostream> #include <queue> #include <cstdlib> #include <ctime> using namespace std; struct Reverse { bool operator()(int x, int y) { return y < x; } }; int main() { priority_queue<int, vector<int>, Reverse> pqi; // Could also say: // priority_queue<int, vector<int>, // greater<int> > pqi; srand(time(0)); for(int i = 0; i < 100; i++) pqi.push(rand() % 25); while(!pqi.empty()) { cout << pqi.top() << ' '; pqi.pop(); } } ///:~
template <class T> struct less : binary_function<T, T, bool> { // Other stuff... bool operator()(const T& x, const T& y) const { return x < y; } };
//: C20:PriorityQueue3.cpp // A more complex use of priority_queue #include <iostream> #include <queue> #include <string> using namespace std; class ToDoItem { char primary; int secondary; string item; public: ToDoItem(string td, char pri ='A', int sec =1) : item(td), primary(pri), secondary(sec) {} friend bool operator<( const ToDoItem& x, const ToDoItem& y) { if(x.primary > y.primary) return true; if(x.primary == y.primary) if(x.secondary > y.secondary) return true; return false; } friend ostream& operator<<(ostream& os, const ToDoItem& td) { return os << td.primary << td.secondary << ": " << td.item; } }; int main() { priority_queue<ToDoItem> toDoList; toDoList.push(ToDoItem("Empty trash", 'C', 4)); toDoList.push(ToDoItem("Feed dog", 'A', 2)); toDoList.push(ToDoItem("Feed bird", 'B', 7)); toDoList.push(ToDoItem("Mow lawn", 'C', 3)); toDoList.push(ToDoItem("Water lawn", 'A', 1)); toDoList.push(ToDoItem("Feed cat", 'B', 1)); while(!toDoList.empty()) { cout << toDoList.top() << endl; toDoList.pop(); } } ///:~
A1: Water lawn A2: Feed dog B1: Feed cat B7: Feed bird C3: Mow lawn C4: Empty trash
//: C20:PriorityQueue4.cpp // Manipulating the underlying implementation #include <iostream> #include <queue> #include <cstdlib> #include <ctime> using namespace std; class PQI : public priority_queue<int> { public: vector<int>& impl() { return c; } }; int main() { PQI pqi; srand(time(0)); for(int i = 0; i < 100; i++) pqi.push(rand() % 25); copy(pqi.impl().begin(), pqi.impl().end(), ostream_iterator<int>(cout, " ")); cout << endl; while(!pqi.empty()) { cout << pqi.top() << ' '; pqi.pop(); } } ///:~
//: C20:PriorityQueue5.cpp // Building your own priority queue #include <iostream> #include <queue> #include <cstdlib> #include <ctime> using namespace std; template<class T, class Compare> class PQV : public vector<T> { Compare comp; public: PQV(Compare cmp = Compare()) : comp(cmp) { make_heap(begin(), end(), comp); } const T& top() { return front(); } void push(const T& x) { push_back(x); push_heap(begin(), end(), comp); } void pop() { pop_heap(begin(), end(), comp); pop_back(); } }; int main() { PQV<int, less<int> > pqi; srand(time(0)); for(int i = 0; i < 100; i++) pqi.push(rand() % 25); copy(pqi.begin(), pqi.end(), ostream_iterator<int>(cout, " ")); cout << endl; while(!pqi.empty()) { cout << pqi.top() << ' '; pqi.pop(); } } ///:~
//: C20:PriorityQueue6.cpp #include <iostream> #include <queue> #include <algorithm> #include <cstdlib> #include <ctime> using namespace std; template<class T, class Compare> class PQV : public vector<T> { Compare comp; bool sorted; void assureHeap() { if(sorted) { // Turn it back into a heap: make_heap(begin(), end(), comp); sorted = false; } } public: PQV(Compare cmp = Compare()) : comp(cmp) { make_heap(begin(), end(), comp); sorted = false; } const T& top() { assureHeap(); return front(); } void push(const T& x) { assureHeap(); // Put it at the end: push_back(x); // Re-adjust the heap: push_heap(begin(), end(), comp); } void pop() { assureHeap(); // Move the top element to the last position: pop_heap(begin(), end(), comp); // Remove that element: pop_back(); } void sort() { if(!sorted) { sort_heap(begin(), end(), comp); reverse(begin(), end()); sorted = true; } } }; int main() { PQV<int, less<int> > pqi; srand(time(0)); for(int i = 0; i < 100; i++) { pqi.push(rand() % 25); copy(pqi.begin(), pqi.end(), ostream_iterator<int>(cout, " ")); cout << "\n-----\n"; } pqi.sort(); copy(pqi.begin(), pqi.end(), ostream_iterator<int>(cout, " ")); cout << "\n-----\n"; while(!pqi.empty()) { cout << pqi.top() << ' '; pqi.pop(); } } ///:~
//: C20:PriorityQueue7.cpp // A priority queue that will hand you a vector #include <iostream> #include <queue> #include <algorithm> #include <cstdlib> #include <ctime> using namespace std; template<class T, class Compare> class PQV { vector<T> v; Compare comp; public: // Don't need to call make_heap(); it's empty: PQV(Compare cmp = Compare()) : comp(cmp) {} void push(const T& x) { // Put it at the end: v.push_back(x); // Re-adjust the heap: push_heap(v.begin(), v.end(), comp); } void pop() { // Move the top element to the last position: pop_heap(v.begin(), v.end(), comp); // Remove that element: v.pop_back(); } const T& top() { return v.front(); } bool empty() const { return v.empty(); } int size() const { return v.size(); } typedef vector<T> TVec; TVec vector() { TVec r(v.begin(), v.end()); // It’s already a heap sort_heap(r.begin(), r.end(), comp); // Put it into priority-queue order: reverse(r.begin(), r.end()); return r; } }; int main() { PQV<int, less<int> > pqi; srand(time(0)); for(int i = 0; i < 100; i++) pqi.push(rand() % 25); const vector<int>& v = pqi.vector(); copy(v.begin(), v.end(), ostream_iterator<int>(cout, " ")); cout << "\n-----------\n"; while(!pqi.empty()) { cout << pqi.top() << ' '; pqi.pop(); } } ///:~
//: C20:PriorityQueue8.cpp // A more compact version of PriorityQueue7.cpp #include <iostream> #include <queue> #include <cstdlib> #include <ctime> using namespace std; template<class T> class PQV : public priority_queue<T> { public: typedef vector<T> TVec; TVec vector() { TVec r(c.begin(), c.end()); // c is already a heap sort_heap(r.begin(), r.end(), comp); // Put it into priority-queue order: reverse(r.begin(), r.end()); return r; } }; int main() { PQV<int> pqi; srand(time(0)); for(int i = 0; i < 100; i++) pqi.push(rand() % 25); const vector<int>& v = pqi.vector(); copy(v.begin(), v.end(), ostream_iterator<int>(cout, " ")); cout << "\n-----------\n"; while(!pqi.empty()) { cout << pqi.top() << ' '; pqi.pop(); } } ///:~