堆的操作(priority_queue容器的介绍)

堆的介绍

堆是一颗完全二叉树,树中每个结点的值都不小于(或不大于)其左右孩子的值。其中,如果父亲结点的值大于或等于孩子结点的值,那么称这样的堆为大顶堆。如果父亲结点的值小于或等于孩子结点的值,那么称这样的堆为小顶堆。
堆的常用操作代码实现:

#include
#include 
using namespace std;
const int maxn=100;
int heap[maxn],n=10;
//对heap数组在[low,high]范围进行向下调整 
//其中low为欲调整结点的数组下标,high一般为堆最后一个元素的数组下标 
void downAdjust(int low,int high){
	int i=low,j=i*2;		//i为欲调节结点,j为其左孩子 
	while(j<=high){		//存在孩子结点
	//如果右孩子存在,且右孩子的值大于左孩子 
		if(j+1<=high&&heap[j+1]>heap[j])
			j=j+1;		//让j存储右孩子下标 
		//如果孩子中最大的权值比欲调整结点i大 
		if(heap[j]>heap[i]){
			swap(heap[j],heap[i]);		//交换最大权值的孩子与欲调整结点i 
			i=j;	//保持i为欲调整结点,j为i的左孩子 
			j=i*2;
		}
		else{
			break;		//孩子的权值均比欲调整结点i小,调整结束 
		}
	}
}
//对heap数组在[low,high]范围进行向上调整 
//其中low为一般设置为1,high表示欲调整结点的数组下标 
void upAdjust(int low,int high){
	int i=high,j=i/2;		//i为欲调节结点,j为其父亲 
	while(j>=high){		//父亲在[low,high]范围内 
		//如果孩子中最大的权值比欲调整结点i小 
		if(heap[j]=1;i--)
		downAdjust(i,n);
} 
//删除堆顶元素
void deleteTop(){
	heap[1]=heap[n--];	//用最后一个元素覆盖堆顶元素,并让元素个数减1 
	downAdjust(1,n);
} 
//添加元素x
void insert(int x){
	heap[++n]=x;		//让元素个数加1,然后将数组末位赋值为x 
	upAdjust(1,n);		//向上调整新加入的结点n 
} 
//堆排序
void heapSort(){
	createHeap();	//建立堆 
	for(int i=n;i>1;i--){		//倒着枚举,直到堆中只有一个元素 
		swap(heap[i],heap[1]);		//交换heap[i]与堆顶 
		downAdjust(1,i-1);		//调整堆顶 
	}
} 
int main()
{
	
}

priority_queue的介绍

但在实际使用过程中往往通过c++STL库中的priority_queue来使用堆。
priority_queue又称优先队列,其底层是用堆来进行实现的。在优先队列中,队首元素一定是当前队列中优先级最高的那一个。
1.priority_queue的定义
要使用优先队列,应先添加头文件#include
其定义的写法和其他STL容器相同,typename可以是任意基本数据类型或容器:

priority_queue name;

2.priority_queue容器内元素的访问
和队列不一样的是,优先队列没有front()函数与back()函数,而只能通过top()函数来访问队首元素(也可以称为堆顶元素),也就是优先级最高的元素。

priority_queue q;
q.top();

3.priority_queue内元素优先级的设置
如何定义优先队列内元素的优先级是运用好优先队列的关键
(1)基本数据类型的优先级设置
优先队列对他们的优先级设置一般是数字大的优先级越高,因此队首元素就是优先队列内元素最大的那个(如果char型,则是字典序最大的)。对基本数据类型来说,下面两种优先队列的定义是等价的:

priority_queue q;
priority_queue,less>q;

第二个参数(vector)填写的是来自承接底层数据结构堆(heap)的容器,该参数类型必须与第一个参数类型相同,第三个参数less则是对第一个参数的比较类,less表示数字大的优先级越大,而greater表示数字小的优先级越大。
(2)结构体的优先级设置

struct fruit{
	string name;
	int price;
	friend bool operator<(fruit f1,fruit f2){
		return f1.price

上面的结构体中对小于号进行重载,重载大于号会编译错误,因为从数学角度来说只需重载小于号,即f1>f2等价于判断f2

注意:
使用top()函数前,建议用empty()判断优先队列是否为空,否则可能因为队空而出现错误。

你可能感兴趣的:(堆的操作(priority_queue容器的介绍))