【适配器模式】实现优先级队列

【适配器模式】由于建立大堆和建立小堆方式相同,代码相似,所以可以通过添加一个比较器(利用Compare,定义伪函数Less和Greater)实现大小数据的比较,防止大量代码重复。

template<class T>
struct Less//小堆调用
{
	bool operator()(const T& L, const T& R)
	{
		return L < R;
	}
};
template<class T>
struct Greater//大堆调用
{
	bool operator()(const T& L, const T& R)
	{
		return L > R;
	}
};

template<class T, template<class>class Compare>
class Heap
{
public:
	Heap();
	Heap(const T* a, size_t size);
protected:
	void _AdjustDown(size_t Parent);//下调--建堆
public:
	vector<T> _a;
};

template<class T, template<class>class Compare>
Heap<T, Compare>::Heap()
:_a(NULL)
{}
template<class T, template<class>class Compare>
Heap<T, Compare>::Heap(const T* a, size_t size)
{
	assert(a);
	_a.reserve(size);//初始化_a(vector模板的使用)
	for (size_t i = 0; i < size; ++i)
	{
		_a.push_back(a[i]);
	}
	//建大堆时,从下往上依次判断并调整堆,使该结点的左右子树都满足大堆
	for (int i = (int)(size - 2) / 2; i >= 0; --i)//不能定义为size_t(无符号)
	{
		_AdjustDown(i);
	}
	//建小堆,类似建大堆的方式,从下向上进行调整堆,使该结点处的左右子树都满足小堆
	//在进行调小堆时,也通过下调实现
}
//下调--建大堆/小堆
template<class T, template<class>class Compare>
void Heap<T, Compare>::_AdjustDown(size_t Parent)
{
	Compare<T> com;
	size_t Child = Parent * 2 + 1;
	while (Child < _a.size())
	{//先进行左右结点的比较,使Child为较大的数的下标,然后与父亲结点进行比较,使较大的数据为父亲结点
		if (Child + 1 < _a.size() && _a[Child] < _a[Child + 1])//存在右结点再进行比较
		{
			++Child;
		}
		if (com(_a[Child], _a[Parent]))//如果用Greater时,为真,则表示子结点大于父亲结点,进行交换
		{
			swap(_a[Child], _a[Parent]);
			Parent = Child;
			Child = Parent * 2 + 1;
		}
		else
		{
			break;
		}
	}
}

优先级队列的实现利用堆实现

template<class T,template<class>class Compare>
class PriorityQueue//优先级队列---调用堆实现
{
public:
	void Push(const T& x)
	{
		_hp.Push(x);
	}
	void Pop()
	{
		_hp.Pop();
	}
	bool Empty()
	{
		return _hp.Empty() == 0;
	}
	T& Front()
	{
		return _hp.GetTop();
	}
	T& Tail()
	{
		size_t size = _hp.Size();
		return _hp._a[size - 1];//将_a设置为public就可以访问
	}
	size_t Size()
	{
		return _hp.Size();
	}
	void PrintPriority()
	{
		_hp.PrintHeap();
	}
private:
	Heap<T, Compare> _hp;
};

测试用例如下:

void Test()
{//利用适配器模式实现优先级队列
	int arr[] = { 10, 16, 18, 12, 11, 13, 15, 17, 14, 19 };
	PriorityQueue<int, Greater> hp;//大数优先级高
	hp.Push(10);
	hp.Push(16);
	hp.Push(18);
	hp.Push(12);
	hp.Push(11);
	hp.Push(13);
	hp.Push(15);
	hp.Push(17);
	hp.Push(14);
	hp.Push(19);
	hp.PrintPriority();
	cout << "empty: " << hp.Empty() << endl;
	cout << "size: " << hp.Size() << endl;
	cout << "front: " << hp.Front() << endl;
	cout << "tail: " << hp.Tail() << endl;
}
时间: 2024-10-13 12:22:53

【适配器模式】实现优先级队列的相关文章

Rabbitmq中的优先级队列操作

1.%% 普通队列操作 in(X, 0, {queue, [_] = In, [], 1}) ->{queue, [X], In, 2}; in(X, 0, {queue, In, Out, Len}) when is_list(In), is_list(Out) -> {queue, [X|In], Out, Len + 1}; 优先级队列操作: in(X, Priority, Q = {queue, [], [], 0}) -> in(X, Priority, {pqueue, []

初学算法-基于最小堆的优先级队列C++实现

笔者近日实现了最小堆类及其派生的优先级队列,特将代码奉上,不足之处还请指出! 在实现优先级队列时,笔者表示萌萌哒没有用过template写派生类,结果写完了出现error: *** was not decleared in this scope..后来各种补上this->才完事,在CSDN(笔者的帖子地址? http://bbs.csdn.net/topics/391806995)上提问后才知道是模板参数依赖,笔者表示涨姿势了.. /**  * The Minimum Heap Class an

【转】java中PriorityQueue优先级队列使用方法

优先级队列是不同于先进先出队列的另一种队列.每次从队列中取出的是具有最高优先权的元素. PriorityQueue是从JDK1.5开始提供的新的数据结构接口. 如果不提供Comparator的话,优先队列中元素默认按自然顺序排列,也就是数字默认是小的在队列头,字符串则按字典序排列. 由于网上的资料大多将优先级队列各个方法属性,很少有实例讲解的,为方便大家以后使用,我就写了个demo~ 如果想实现按照自己的意愿进行优先级排列的队列的话,需要实现Comparator接口.下面的方法,实现了根据某个变

STL学习系列七:优先级队列priority_queue容器

1.简介 最大值优先级队列.最小值优先级队列 优先级队列适配器 STL priority_queue 用来开发一些特殊的应用,请对stl的类库,多做扩展性学习 如果我们给每个元素都分配一个数字来标记其优先级,不妨设较小的数字具有较高的优先级,这样我们就可以在一个集合中访问优先级最高的元素并对其进行查找和删除操作了.这样,我们就引入了优先级队列 这种数据结构. 优先级队列(priority queue) 是0个或多个元素的集合,每个元素都有一个优先权,对优先级队列执行的操作有(1)查找(2)插入一

优先级队列及小顶堆排序

优先级队列及小顶堆排序实现 /** @file          HeapSort.h *  @copyright     personal *  @brief         优先级队列及堆排序 *  @version       V1.0.0 *  @author        fangyuan *  @date          2015/12/31 *  @note          测试版本 */ #include "iostream" using namespace std

初学图论-Dijkstra单源最短路径算法基于优先级队列(Priority Queue)的实现

这一次,笔者使用了STL库中的优先级队列(Priority Queue)来完成Dijkstra算法中extract-min()语句(即从未选中的节点中选取一个距离原点s最小的点)的功能.由于优先级队列的插入.删除操作只需要logn的时间花费,因此降低了不少运行时间. 本文使用C++实现了这一基本算法.参考<算法导论>第24.3节. /**  * Dijkstra's Single Source Shortest Path Algorithm in C++  * Time Cost : O(Ml

STL之优先级队列priority_queue

摘要: priority_queue,自适应容器(即容器适配器):不能由list来组建: 最大值优先级队列(最大值始终在对首,push进去时候) 最小值优先级队列: 优先级队列适配器 STL  priority_queue priority_queue<int, deque<int> > pg; priority_queue<int, vector<int> > pg; STL中实现的方法: pg.empty(); pg.size(); pg.top();

队列的应用:优先级队列

优先级队列:如果我们给每个元素都分配一个数字来标记其优先级,不妨设较小的数字具有较高的优先级,这样我们就可以在一个集合中访问优先级最高的元素并对其进行查找和删除操作了. 优先级队列(priority queue)是0个或多个元素的集合,每个元素都有一个优先权,对优先级队列执行的操作有(1)查找(2)插入一个新元素(3)删除 一般情况下,查找操作用来搜索优先权最大的元素,删除操作用来删除该元素 .对于优先权相同的元素,可按先进先出次序处理或按任意优先权进行. 以上是网上常见的对优先级队列的描述.偷

JAVA优先级队列测试

package code.test; import java.util.Comparator; import java.util.Iterator; import java.util.PriorityQueue; import java.util.Queue; /** * 实验表明,在java中: * 1.优先级队列打印或者迭代,得到的输出顺序为堆结构数组的顺序,大致有序但不完全保证顺序 * 2.由于堆排序是不稳定排序,在优先级相同的情况下,元素不会保持原来的顺序输出 * Created by