priority_queue的用法「建议收藏」

priority_queue的用法「建议收藏」priority_queue本质是一个堆。1.头文件是#include<queue>2.关于priority_queue中元素的比较模板申明带3个参数:priority_queu

大家好,又见面了,我是你们的朋友全栈君。

priority_queue本质是一个堆。

1. 头文件是#include<queue>

2. 关于priority_queue中元素的比较

  模板申明带3个参数:priority_queue<Type, Container, Functional>,其中Type 为数据类型,Container为保存数据的容器,Functional 为元素比较方式。

  Container必须是用数组实现的容器,比如vector,deque等等,但不能用 list。STL里面默认用的是vector。

2.1 比较方式默认用operator<,所以如果把后面2个参数缺省的话,优先队列就是大顶堆(降序),队头元素最大。特别注意pair的比较函数

  以下代码返回一个降序输出:

 1 #include <iostream>
 2 #include <queue>
 3 using namespace std;
 4 int main(){
 5     priority_queue<int> q;
 6     for( int i= 0; i< 10; ++i ) q.push(i);
 7     while( !q.empty() ){
 8         cout<<q.top()<<endl;
 9         q.pop();
10     }
11     return 0;
12 }

 

  以下代代码返回pair的比较结果,先按照pair的first元素降序,first元素相等时,再按照second元素降序:

 1 #include<iostream>
 2 #include<vector>
 3 #include<queue>
 4 using namespace std;
 5 int main(){
 6     priority_queue<pair<int,int> > coll;
 7     pair<int,int> a(3,4);
 8     pair<int,int> b(3,5);
 9     pair<int,int> c(4,3);
10     coll.push(c);
11     coll.push(b);
12     coll.push(a);
13     while(!coll.empty())
14     {
15         cout<<coll.top().first<<"\t"<<coll.top().second<<endl;
16         coll.pop();
17     }
18     return 0;
19 }

 

 

2.2 如果要用到小顶堆,则一般要把模板的3个参数都带进去。STL里面定义了一个仿函数greater<>,基本类型可以用这个仿函数声明小顶堆

  以下代码返回一个升序输出:

 1 #include <iostream>
 2 #include <queue> 
 3 using namespace std;
 4 int main(){
 5     priority_queue<int, vector<int>, greater<int> > q;
 6     for( int i= 0; i< 10; ++i ) q.push(10-i);
 7     while( !q.empty() ){
 8         cout << q.top() << endl;
 9         q.pop();
10     }
11     return 0;
12 }

 

  以下代代码返回pair的比较结果,先按照pair的first元素升序,first元素相等时,再按照second元素升序: 

 1 #include<iostream>
 2 #include<vector>
 3 #include<queue>
 4 using namespace std;
 5 int main(){
 6     priority_queue<pair<int,int>,vector<pair<int,int> >,greater<pair<int,int> > > coll;
 7     pair<int,int> a(3,4);
 8     pair<int,int> b(3,5);
 9     pair<int,int> c(4,3);
10     coll.push(c);
11     coll.push(b);
12     coll.push(a);
13     while(!coll.empty())
14     {
15         cout<<coll.top().first<<"\t"<<coll.top().second<<endl;
16         coll.pop();
17     }
18     return 0;
19 }

 

 

2.3 对于自定义类型,则必须重载operator<或者重写仿函数。

2.3.1 重载operator<的例子:返回true时,说明左边形参的优先级低于右边形参

 1 #include <iostream>
 2 #include <queue> 
 3 using namespace std;
 4 struct Node{
 5     int x, y;
 6     Node(int a=0, int b=0):
 7         x(a),y(b){}
 8 };
 9 bool operator<(Node a, Node b){//返回true时,说明a的优先级低于b
10     //x值较大的Node优先级低(x小的Node排在队前)
11     //x相等时,y大的优先级低(y小的Node排在队前)
12     if( a.x== b.x ) return a.y> b.y;
13     return a.x> b.x; 
14 }
15 int main(){
16     priority_queue<Node> q;
17     for( int i= 0; i< 10; ++i )
18     q.push( Node( rand(), rand() ) );
19     while( !q.empty() ){
20         cout << q.top().x << ' ' << q.top().y << endl;
21         q.pop();
22     }
23     return 0;
24 }

 

自定义类型重载operator<后,声明对象时就可以只带一个模板参数

但此时不能像基本类型这样声明priority_queue<Node,vector<Node>,greater<Node> >,原因是greater<Node>没有定义,如果想用这种方法定义则可以重载operator >。

例子:返回的是小顶堆。但不怎么用,习惯是重载operator<。

 1 #include <iostream>
 2 #include <queue>
 3 using namespace std;
 4 struct Node{
 5     int x, y;
 6     Node( int a= 0, int b= 0 ):
 7         x(a), y(b) {}
 8 };
 9 bool operator>( Node a, Node b ){//返回true,a的优先级大于b
10     //x大的排在队前部;x相同时,y大的排在队前部
11     if( a.x== b.x ) return a.y> b.y;
12     return a.x> b.x; 
13 }
14 int main(){
15     priority_queue<Node,vector<Node>,greater<Node> > q;
16     for( int i= 0; i< 10; ++i )
17     q.push( Node( rand(), rand() ) );
18     while( !q.empty() ){
19         cout << q.top().x << ' ' << q.top().y << endl;
20         q.pop();
21     }
22     return 0;
23 }

 

2.3.2 重写仿函数的例子(返回值排序与2.3.1相同,都是小顶堆。先按x升序,x相等时,再按y升序):

 1 #include <iostream>
 2 #include <queue>
 3 using namespace std;
 4 struct Node{
 5     int x, y;
 6     Node( int a= 0, int b= 0 ):
 7         x(a), y(b) {}
 8 };
 9 struct cmp{
10     bool operator() ( Node a, Node b ){//默认是less函数
11         //返回true时,a的优先级低于b的优先级(a排在b的后面)
12         if( a.x== b.x ) return a.y> b.y;      
13         return a.x> b.x; }
14 };
15 int main(){
16     priority_queue<Node, vector<Node>, cmp> q;
17     for( int i= 0; i< 10; ++i )
18     q.push( Node( rand(), rand() ) );
19     while( !q.empty() ){
20         cout << q.top().x << ' ' << q.top().y << endl;
21         q.pop();
22     }
23     return 0;
24 } 

 

 

参考:http://www.cnblogs.com/flyoung2008/articles/2136485.html

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/154473.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)


相关推荐

  • 实战DeviceIoControl 之中的一个:通过API訪问设备驱动程序

    实战DeviceIoControl 之中的一个:通过API訪问设备驱动程序

  • Django(53)二次封装Response

    Django(53)二次封装Response前言有时候我们使用drf的Response,会发现默认返回的格式不太友好,每次我们都需要写入以下的格式returnResponse({"status":0,"

  • stm32收发 wiegand 韦根协议开发详解

    stm32收发 wiegand 韦根协议开发详解在刚开始接触到韦根接口时,知道这是一种门禁相关的传输协议。其中有两种比较常用的韦根数据格式,韦根26和韦根34,其中韦根26是开放的,韦根34开不开放我不知道(看样子不开放),但是在网上还是能看到韦根34的代码协议,下面介绍一下韦根26以及韦根34的相关内容。Wiegand26格式:各数据位的含义:第1位: 为输出数据2—13位的偶校验位第2-9位:…

    2022年10月27日
  • YUI3 使用总结

    YUI3 使用总结1. YUI3总体认识1.1 面向对象的JS编程,RIA工具:面向对象的JS编程,主要体现的以下几个方面:1. 继承JS有三种继承方式:javascript中继承一般分为三种方式:”类式继承”,”原型继承”,”掺元类”2. 封装:JS的Function自身就实现了对变量的封装,局部变量等。Object对性的属性也可以实现一定的封装效果3. 接口和抽象类YUI3…

  • python interpolate.interp1d,Python interp1d与UnivariateSpline

    python interpolate.interp1d,Python interp1d与UnivariateSplineI’mtryingtoportsomeMatLabcodeovertoScipy,andI’vetriedtwodifferentfunctionsfromscipy.interpolate,interp1dandUnivariateSpline.Theinterp1dresultsmatchtheinterp1dMatLabfunctio…

  • HttpServletRequest

    HttpServletRequest代表的是我们的响应对象HttpServletRequest概述service方法中的request的类型是ServletRequest,而doGet/doPost方法的request的类型是Htt

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号