学习笔记(三)——STL

上一章说到了<queue>的使用,下面我们先来介绍一个<queue>的姊妹容器——<priority_queue>

"priority_queue"

        priority_queue优先队列容器和queue一样,只能从队列尾部插入元素,从队列首部删除元素。但它有一个特性,就是队列中最大元素总是位于队首,所以出队时,并非按照FIFO的顺序进行,而是将队列中最大的元素弹出。这点类似于给队列中元素进行了由大到小的顺序排序。元素的比较规则默认为按元素的大小进行排序,也可以重载<运算符来重新定义比较规则.

        priority_queue优先队列被定义在头文件<quque>里,使用时需要用priority_queue<int> pq这种方式声明。

自定义类型也可以构成优先队列,但必须为每个元素定义一个优先级,。这个优先级并不需要一个确定的数字,只要能比较大小即可。类似于给sort()函数用的cmp。

        下面是一个例子,实现了“个位数大的整数优先级反而小”的优先队列。

<span style="font-family:Courier New;">struct cmp{
    bool operator()(const int a,const int b)const{
        //a的优先级比b小时返回true
    return a%10 > b%10;
    }
};</span>
对于一些常见的优先队列,STL提供了更为简单的定义方式,如“越小的整数优先级越高”这种队列,可以直接采用下面的定义方式:

<span style="font-family:Microsoft YaHei;">priority_queue<int,vector<int>,greater<int> > pq;</span>
用例题来展示用法吧。

UVA136,丑数(Ugly Numbers)

题目大意:丑数是不能被2,3,5以外其他素数整除的数。把丑数从小到大排列起来,结果如下:

1,2,3,4,5,6,8,9,10,12,15……

求第n个丑数。

分析:

本题实现方法很多,此处采取生成丑数并储存的方法,可以用一个priority_queue来储存生成的丑数,每次取出最小的丑数,生成三个新的丑数。同时要判断这个丑数是否已经生成过。

<span style="font-family:Courier New;">#include<queue>
#include<cstdio>
#include<algorithm>
#include<iostream>
#include<set>

#define LL long long

const int coeff[3]={2,3,5};

using namespace std;

int main()
{
	priority_queue<LL,vector<LL>,greater<LL> > pq;
	set<LL> s;
	pq.push(1);
	s.insert(1);
	int n;
	cin>>n;
	for(int i=1;;i++)
    {
        LL x = pq.top();
        pq.pop();
        if(i==n)
        {
            cout<<"The "<<n<<"'th ugly number is "<<x<<endl;
            break;
        }
        for(int j=0;j<3;j++)
        {
            LL x2=x*coeff[j];
            if(!s.count(x2))
            {
                s.insert(x2);
                pq.push(x2);
            }
        }
    }

    return 0;
}
</span>

如果优先队列的元素类型是结构体,那么我们可以重“<”运算符来实现修改队列的优先性。

例程:

<span style="font-family:Courier New;">#include<queue>
#include<iostream>
#include<set>

#define LL long long

using namespace std;

struct Info{
    string name;
    float score;
    //重载<操作符,指定优先规则
    bool operator < (const Info &a) const
    {
        //按score大小排列。若要由大到小排列,使用“>”即可。
        return a.score<score;
    }
};

int main()
{
	//定义优先队列
	priority_queue<Info> pq;
	//定义结构体变量 作临时存储
	Info info;
	//入队
	info.name="jack";
	info.score=68.5;
	pq.push(info);
	info.name="bomi";
	info.score=18.5;
	pq.push(info);
	info.name="peti";
	info.score=90.0;
	pq.push(info);

	//元素全部出队
	while(pq.empty()!=true)
    {
        cout<<pq.top().name<<" : "<<pq.top().score<<endl;
        //出队,删除队首元素
        pq.pop();
    }
    return 0;
}
</span>




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值