转载自https://blog.csdn.net/crayondeng/article/details/16332169
STL 中栈的使用方法(stack)
#include <stack>
基本操作:
push(x) 将x加入栈中,即入栈操作
pop() 出栈操作(删除栈顶),只是出栈,没有返回值
top() 返回第一个元素(栈顶元素)
size() 返回栈中的元素个数
empty() 当栈为空时,返回 true
基本操作:
push(x) 将x压入队列的末端
pop() 弹出队列的第一个元素(队顶元素),注意此函数并不返回任何值
front() 返回第一个元素(队顶元素)
back() 返回最后被压入的元素(队尾元素)
empty() 当队列为空时,返回true
size() 返回队列的长度
---------- 栈和队列的用法都相对简单,下面详细介绍优先队列的用法 -----------
STL 中优先队列的使用详细介绍(priority_queu)
#include <queue>
基本操作:
empty() 如果队列为空返回真
pop() 删除对列首元素
push() 加入一个元素
size() 返回优先队列中拥有的元素个数
top() 返回优先队列首元素
在默认的优先队列中,优先级高的先出队。
标准库默认使用元素类型的 < 操作符来确定它们之间的优先级关系。
(1)优先队列的第一种用法,这是最常用的默认的优先级用法,也就是优先级高的先出队列,例如说一个int优先队列,那么出队的时候就是int大的先出队列。
下面给出一个例子:
1 #include <iostream> 2 #include <queue> 3 using namespace std; 4 int main() 5 { 6 priority_queue<int> q; 7 for(int i = 1;i <= 5;i++) 8 { 9 q.push(i); 10 } 11 for(int i = 0;i < 5;i++) 12 { 13 cout<<q.top()<<endl; 14 q.pop(); 15 } 16 return 0; 17 }
运行结果可想而知,就是从大到小的: 5 4 3 2 1
(2)那么如果想要优先队列中低优先级的元素先出队列,怎么办呢? --- 自定义优先级
①方法一:我们可以传入一个比较函数,使用functional头文件中的greater函数对象作为比较函数
注意:首先要添加头文件:#include <functional>
priority_queue< int,vector<int>,greater<int> > q; // 注意:> > 误写成>> 会报错
这样我们就创建了一个低优先级元素先出对列的优先队列。
修改上面的例子,运行,就会发现,输出的顺序变成了:1 2 3 4 5。
当然,与greater相对的less,如果传入less这个比较函数,那么就是高优先级元素先出队列了。
priority_queue< int,vector<int>,less<int> > q;
priority_queue<int> q;
以上创建的优先队列是相同的。
②方法二:自己实现比较函数
1 struct cmp1 2 { 3 bool operator ()(int x,int y) 4 { 5 return x>y; //小值优先 6 } 7 };
priority_queue<int,vector<int>,cmp1 > q;
这样就创建了一个小值元素先出队列的优先队列,这里的 cmp1 作用就相当于 greater同理我们可以写出:
1 struct cmp2 2 { 3 bool operator ()(int x,int y) 4 { 5 return x<y; //大值优先 6 } 7 };
priority_queue<int,vector<int>,cmp2 > q;
这里就是创建了一个大值元素先出队列的优先队列,这里的 cmp2 作用也就是相当于 less
(3)假如优先队列中的元素是一个结构对象或者是类对象,那么如何重新自定义其优先级比较呢?
例子一:定义一个结构体,这个结构体只有一个元素 x 。
①低优先级元素先出队列,也就是x值小的先出队列。
1 struct number1 2 { 3 int x; 4 bool operator < (const number1 &a) const 5 { 6 return x>a.x;//小值优先 7 } 8 };
1 number1 num1[5]; 2 priority_queue<number1>q; 3 for(int i = 1; i <= 5; i++) 4 { 5 num1[i].x = i; 6 q.push(num1[i]); 7 } 8 for(int i = 1; i <= 5; i++) 9 { 10 cout<<q.top().x<<endl; 11 q.pop(); 12 }
输出: 1 2 3 4 5
②高优先级元素先出队列,也就是x值大的先出队列。1 struct number2 2 { 3 int x; 4 bool operator < (const number2 &a) const 5 { 6 return x<a.x;//大值优先 7 } 8 };
注意到:结构体中重载的运算符只可以是 <, 因为标准库默认使用元素类型的 < 操作符来确定它们之间的优先级关系,如果重载 > ,那么会编译错误。
例子二:在上面的例子中,我们是将 结构体中的 x 的大小当做是优先级比较值了。下面给出另一例子,这个例子更具有一般性。
1 struct node 2 { 3 friend bool operator < (node n1, node n2) 4 { 5 return n1.priority < n2.priority; 6 } 7 int priority; 8 int value; 9 };
在这个结构体中,priority表征优先级值。
1 priority_queue<node> qn; 2 node b[5]; 3 b[0].priority = 6; b[0].value = 1; 4 b[1].priority = 9; b[1].value = 5; 5 b[2].priority = 2; b[2].value = 3; 6 b[3].priority = 8; b[3].value = 2; 7 b[4].priority = 1; b[4].value = 4; 8 9 for(int i = 0; i < 5; i++) 10 qn.push(b[i]); 11 cout<<"优先级"<<' '<<"值"<<endl; 12 for(int i = 0; i < 5; i++) 13 { 14 cout<<qn.top().priority<<' '<<qn.top().value<<endl; 15 qn.pop(); 16 }
输出结果为:
优先级 值
9 5
8 2
6 1
2 3
1 4
//总结一下,结构体数据排序的快速写法 //以后在遇到需要写的时候,不要迟疑快速写完 struct node { int u, v, w; }a[10000]; //假设该结构体有3个元素 //现在仅实现结构体数组按照w的值从小到大的排序 //1.基于C++的重载写法,写在结构体的定义内 如下: struct node { int u, v, w; bool operator <(const node &x)const { return w<x.w; //升序排列 } }; //现在提高要求:如果w相同,则按照v的值升序排列(降序也可实现) struct node { int u, v, w; bool operator < (const node &x)const { if(w==x.w) return v<x.v; //return x.v<v; //按照的v的值降序排列 else return w<x.w; } }; //同理,也可对第三元素进行参与某种顺序的排列 这种写法直接调用<algorithm>里的函数即可:sort(a, a+n); //2.自己写比较算子函数的写法 // sort函数是可以支持调入第三参量(比较函数)<br>// 调用方式:sort(a, a+n, cmp); struct node { int u, v, w; }; bool cmp(node a, node b) { if(a.w < b.w ) //按照w的值进行的是:升序排列 ! return true; else return false; } //还可以这样写 bool cmp(node a, node b) { return a.w<b.w; //升序 } //当然cmp函数也可以写的稍微复杂点,也就是说,按照优先级对结构体的多个成员按照某种规则排序,就像刚才上面写的 //先按照w的值升序排序,如果w相等,再按照v的值升序排序 bool cmp(node a, node b) { if(a.w==b.w) return a.v<b.v; else return a.w<b.w; } //或者这样写 bool cmp(node a, node b) { if(a.w<b.w) return true; if(a.w==b.w && a.v<b.v ) return true; return false; }