赞
踩
1、 优先队列是一种容器适配器,根据严格的弱排序标准,它的第一个元素总是它所包含的元素中最大的。
2、 此上下文类似于堆,在堆中可以随时插入元素,并且只能检索最大堆元素(优先队列中位于顶部的元素)。
3、 优先队列被实现为容器适配器,容器适配器即将特定容器类封装作为其底层容器类,queue提供一组特定的成员函数来访问其元素。元素从特定容器的“尾部”弹出,其称为优先队列的顶部。
4、 底层容器可以是任何标准容器类模板,也可以是其他特定设计的容器类。容器应该可以通过随机访问迭代器访问,并支持以下操作:
empty() | 检测容器是否为空 |
---|---|
size() | 返回容器中有效元素个数 |
front() | 返回容器中第一个元素的引用 |
push_back() | 在容器尾部插入元素 |
pop_back() | 删除容器尾部元素 |
5、标准容器类 vector和deque(双端队列) 满足这些需求。默认情况下,如果没有为特定的priority_queue类实例化指定容器类,则使用vector。
6、需要支持随机访问迭代器,以便始终在内部保持 堆结构。容器适配器通过在需要时自动调用算法函数make_heap、push_heap和pop_heap来自动完成此操作。
#include <iostream> #include <functional> #include <queue> using namespace std; //仿函数,函数对象 //struct Less //{ // bool operator()(int left, int right) // { // return left < right; // } //}; template<class T> struct Less { bool operator()(const T& left, const T& right) { return left < right; } }; int main() { //priority_queue<int> pq;//默认是传less比较生成大堆 priority_queue<int, vector<int>, greater<int>> pq;//也可传greater,此时生成的是小堆 pq.push(3); pq.push(2); pq.push(5); pq.push(0); pq.push(7); pq.push(3); while (pq.empty() != 1) { cout << pq.top() << " "; pq.pop(); } cout << endl; int a = 1; int b = 2; Less<int> less;//是一个对象,但是可以像使用一个函数一样使用它,称为仿函数 cout << less(a, b) << endl; cout << less.operator()(a, b) << endl; return 0; }
#pragma once #include <iostream> #include <vector> #include <deque> using namespace std; template<class T, class Container = vector<T>, class Compare = less<T>> class PriorityQueue { public: void Adjustdown(size_t parent)//向下调整算法 { size_t child = parent * 2 + 1; while (child < _con.Size()) { if (_con[child] < _con[child + 1]) ++child; if (_con[parent] < _con[child]) { swap(_con[parent], _con[child]); parent = child; child = parent * 2 + 1; } else { break; } } } void AdjustUp(size_t child)//向上调整算法 { size_t parent = (child - 1) / 2; while (child) { if (_con[parent] < _con[child]) { swap(_con[parent], _con[child]); child = parent; parent = (child - 1) / 2; } else { break; } } } void Push(const T& x)//尾插 { _con.push_back(x); AdjustUp(_con.size() - 1); } void Pop()//头删 { swap(_con[0], _con[_con.Size() - 1]); _con.pop_back(); Adjustdown(0); } const T& Top() { return _con[0]; } size_t Size() const { return _con.size(); } bool Empty() const { return _con.empty(); } private: Container _con; }; class Goods { public: bool operator<(const Goods r) const { return _price < r._price; } public: int _price; int _sales_volume; int _evaluation; int _comprehensive; }; struct GoodsPriceLess { bool operator()(const Goods& l, const Goods& r) { return l._price < r._price; } }; struct GoodsPriceGreater { bool operator()(const Goods& l, const Goods& r) { return l._price > r._price; } }; void TestPriorityQueue() { PriorityQueue<Goods, vector<Goods>, GoodsPriceLess> goodspq; goodspq.Push(Goods{ 1, 2, 3, 4 }); goodspq.Push(Goods{ 4, 3, 2, 1 }); Goods top = goodspq.Top(); cout << top._price << endl; cout << top._sales_volume << endl; cout << top._evaluation << endl; cout << top._comprehensive << endl; }
注: 1、这里简单实现了优先队列的功能,底层容器用的是vector,在这里我没写优先级队列的构造函数以及析构函数,用了系统默认生成的即可。
2、测试函数中我给出了一个自定义类型,是为了测试一下自己写的仿函数,我们都知道显示生活中有很多时候我们比较时不仅仅只比较一方面,就像是一个商品我们可能会按价格比较,也可能按人气比较,或是按综合评价比较,这个时候我们用仿函数就比较方便了,我们只要按照需求写一个对应比较的仿函数就可以实现相关功能。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。