STL之queue、priority_queue学习总结(C++)

概述

  1. STL提供3种容器适配器:stack、queue、priority_queue。容器适配器不是第一类容器,因为它们不提供存放数据的实际数据结构的实现方法。而且容器适配器不支持迭代器。容器适配器的好处:程序员可以选择相应的基础数据结构。
  2. queue模板类让底层类(默认是deque)展示典型的队列接口。
  3. queue类的限制比deque更多,不允许随机访问队列元素、不允许遍历队列。而是提供的功能可以从基础数据结构的结尾插入或在开头删除(先进先出FIFO)。priority_queue提供的功能可以按排列顺序插入基础数据结构,并从基础数据结构的前面删除。
  4. queue能用list和deque实现。priority_queue能用vector和deque实现。默认情况下,queue用deque实现。priority_queue用vector实现。 这两个实现都是其最佳性能。
  5. 在priority_queue中增加元素时,该元素自动按优先顺序插入,使最高优先级元素(默认是最大值)首先从priority_queue中取出。
    通常是用堆排序技术实现的。 这种数据结构成为堆(heap)。默认的元素比较器是less。
    优先队列常见用法是是处理堆的有关操作。默认优先队列是大顶堆。
  6. priority_queue插入与删除
    -push操作:根据优先顺序将元素插入相应位置(先调用基础容器的push_back函数,然后用堆排序重新排列元素);
    -pop操作:删除最高优先级元素(删除堆顶上的元素后调用基础容器的pop_back函数)。

具体用法

0. 头文件

#include<queue>

1. 声明和初始化

1.1 queue

//声明queue,默认以deque容器实现
	queue<int>q1;
//声明queue,以list容器实现
	queue<int, list<int>>q1;

//声明一个int类型的queue2,将queue1的元素复制给queue2
	queue<int>queue2=queue1;
或	queue<int> queue2(queue1);

1.2 priority_queue

1.2.1 基本数据类型,以int为例
//声明priority_queue,默认以vector容器实现,默认排序是从大到小
	priority_queue<int>q11;
//声明priority_queue,以deque容器实现,默认排序是从大到小
	priority_queue<int, deque<int>>q11;

//声明priority_queue,设置排序为:从小到大,需要三个参数
//参数内容:存储元素类型、容器类型、顺序定义
	priority_queue<int, vector<int>,greater<int>>q11;

1.2.2 结构体

对于结构体而言,排序顺序需要自己实现。

//法一:在结构体里内重载比较函数(使用友元)
struct A{
	int x;
	int y;
	A(int _x, int _y):x(_x),y(_y) {}

	friend bool operator < (A a, A b) {
		return a.y > b.y;    //重载小于号使得小的先出队列    
	}
};

priority_queue<A> p1; //或priority_queue<A,vector<A>> p1;

//法二:在结构体里内重载比较函数
struct A{
	int x;
	int y;
	A(int _x, int _y):x(_x),y(_y) {}

	bool operator < (const A &a) const {
		return y > a.y;    //重载小于号使得小的先出队列    
	}
};

priority_queue<A> p1; //或priority_queue<A,vector<A>> p1;

//法三:在结构体外
struct A{
	int x;
	int y;
	A(int _x, int _y):x(_x),y(_y) {}
};
struct cmp {
	bool operator ()(const A &a, const A &b) {
		return a.y > b.y; //重载使得小的先出队列
	}
};

priority_queue<A, vector<A>,cmp> p1; //定义需要3个参数


2. 常用函数(查询)

未特别标注的都是queue、priority_queue通用的函数方法。

2.1 empty()

queue1.empty(); //返回值bool类型,若queue1为空,则返回true

2.2 size()

queue1.size(); //返回值为int类型,queue1当前存放的元素的个数

2.3 front()——queue;

条件是queue不为空

queue1.front(); //返回队列头部元素

2.4 back()——queue

条件是queue不为空

queue1.back(); //返回队列末尾元素

2.5 top()——priority_queue

条件是priority_queue不为空

queue1.top(); //返回队列头部元素

2.6 输出

//设置一个输出函数
void display_queue(queue<int> nums) {
	while (!nums.empty()) {
		cout << nums.front() << " ";
		nums.pop();
	}
	cout << endl;
}

3. 常用函数(操作)

3.1 push()

//在queue1的队列末尾放入元素2
	queue1.push(2)

3.2 emplace()

push()函数和emplace()都是在队列这个容器的末尾插入一个新的元素。

  • push() 实际上是调用的底层容器的push_back()函数,新元素的值是push函数参数的一个拷贝。
  • emplace() 实际上是调用的底层容器的emplace_back()函数,新元素的值是在容器内部就地构造的,不需要移动或者拷贝。
//在stack1的栈顶放入元素2
	stack1.emplace(2);

3.3 pop()

//删除queue1队列头部元素
	queue1.pop()

3.4 swap()

//将queue1和queue2交换
	queue1.swap(queue2);

4. 实际使用出现的问题和方案

4.1 插入时判断是否已存在相同的元素值?

由于没有find()、count()函数,无法直接调用函数得知队列是否存在相同值。

4.2 将某个值删除(若有重复值)

int key=pq.top();
while(key==pq.top()){
	pq.pop();
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值