1. 程式人生 > >隊列的應用:優先隊列

隊列的應用:優先隊列

推斷 mil sim namespace data gda hang ++ cpp

優選隊列:假設我們給每一個元素都分配一個數字來標記其優先級。最好還是設較小的數字具有較高的優先級,這樣我們就能夠在一個集合中訪問優先級最高的元素並對其進行查找和刪除操作了。

優先隊列(priority queue)是0個或多個元素的集合,每一個元素都有一個優先權,對優先級隊列運行的操作有(1)查找(2)插入一個新元素(3)刪除 普通情況下,查找操作用來搜索優先權最大的元素。刪除操作用來刪除該元素 。對於優先權同樣的元素,可按先進先出次序處理或按隨意優先權進行。


以上是網上常見的對優先級隊列的描寫敘述。偷個懶,直接抄過來。主要是它描寫敘述的非常清楚。

重要的是優先隊列與普通隊列的差別:

  1. 刪除時。總是刪除優先級最大的,並不是僅僅是普通的隊頭出隊。
  2. 普通隊列不存在查找操作。優先級隊列的查找,一定是查找優先級最大的。
以下我們使用順序存儲結構實現優先級隊列,其他的細節看代碼: 類定義和類實現
#include<iostream>
#include<iomanip>
using namespace std;
const int MAX = 10;
typedef struct node    //priority queue node
{
	int no;        //任務編號
	int priority;   //優先級
}PQNode;
class PQueue    //優先隊列類
{
private:
	PQNode *base;
	int size;     //隊列大小
public:
	//構造函數 
	PQueue();
	//析構函數 
	~PQueue();
	//獲取隊列大小 
	int getSize()
	{return size;}  
	//推斷隊列是否為空 
	bool empty()
	{return size == 0;}
	//清空
	void clear()
	{size = 0;}
	//重載運算符<
	bool friend operator<(PQNode node1, PQNode node2);
	//入隊
	bool push(PQNode);
	//出隊
	bool pop(PQNode&);
	//查找
	bool find(PQNode&);
	//遍歷 
	void queueTraverse(); 
};
PQueue::PQueue()
{
	base = new PQNode[MAX];
	size = 0;
}
PQueue::~PQueue()
{
	delete[]base;
}
bool operator<(PQNode node1, PQNode node2)
{
	return node1.priority < node2.priority;
}
bool PQueue::push(PQNode node)
{
	int i;
	for (i=0; i < size; i++)
	{
		if (node.no == base[i].no)  //對於已存在的任務編號更新優先級 
		{
			base[i].priority = node.priority;
			break;
		}
	}
	if (i < size || (i == size && size < MAX))
	{
		if (i == size)
		base[size++] = node;
		return true;
	}
	//已無空間存放新節點 
	return false;
}
bool PQueue::pop(PQNode &node)
{
	if (size == 0)
		return false;
	int index = 0;
	for (int i = 1; i < size; i++)
	{
		if (base[i] < base[index])  //若是沒有重載<。則這裏必須寫成base[i].priority<base[index].priority
			index = i;
	}
	node = base[index];
	/*
	出隊後,index位置該怎樣填補?
	方法多種:
	一、index後的元素依次前移
	二、直接用最後一個元素填到index位置
	建議使用第一種 
	*/
	size--;
	for (int i = index; i < size; i++)
		base[i] = base[i + 1];
	return true;
}
bool PQueue::find(PQNode &node)
{
	if (size == 0)
		return false;
	int index = 0;
	for (int i = 1; i < size; i++)
	{
		if (base[i] < base[index])
			index = i;
	}
	node = base[index];
	return true;
}
void PQueue::queueTraverse()
{
	if(!empty())
	{
		int i=0;
		cout<<"編號"<<" "<<"優先級"<<endl;
		while (i < size)
		{
			cout<<setw(4)<<base[i].no<<setw(4)<<base[i].priority<<endl;
			i++;
		}
	}
}
主函數
int main()
{
	cout<<"******優先級隊列演練******"<<endl;
	PQueue pqueue;
	cout<<"隊列眼下的狀態是";
	pqueue.empty()?cout<<"空!"<<endl:cout<<"非空!"<<endl;
	PQNode node;
	cout<<"輸入任務號和優先級(一組一行),輸入0 0結束"<<endl;
	while(cin>>node.no>>node.priority && node.no && node.priority)
		pqueue.push(node);
	cout<<"打印隊列"<<endl;
	pqueue.queueTraverse();
	cout.setf(ios::left);
	cout<<"查找優先級最高的"<<endl;
	pqueue.find(node)?

cout<<"編號是"<<setw(4)<<node.no<<"優先級是"<<setw(4)<<node.priority<<endl:cout<<"空隊列。無法查找。"<<endl; cout<<"隊列清空"<<endl; pqueue.clear(); cout<<"隊列眼下的狀態是"; pqueue.empty()?cout<<"空!

"<<endl:cout<<"非空!

"<<endl; system("pause"); return 0; }

執行: 技術分享

完整代碼下載:優先隊列

專欄文件夾看這裏:
  • 數據結構與算法文件夾
  • c指針


隊列的應用:優先隊列