hdu 4393 Throw nails(优先队列)

题意:n个人比赛(标号1~n),每个人有两个速度 f 和 s,分别代表第1s的速度和之后的速度。每秒结束时第一名淘汰,输出所有人的淘汰顺序。如果并列第一,那么淘汰标号小的。0<=f<=500,0<s<=100

思路:可以看到0<s<=100,相同s的放到一个优先队列里,优先队列先按 f 从大到小排,f 相同按标号从小到大排。

每次让s从1到100枚举,取出距离最大的即可。

#include<iostream>
#include<stdio.h>
#include<queue>
using namespace std;

struct node{
    int index;
    int f;
    bool operator < (const node &a) const {
        if(f!=a.f)return f<a.f;//最大值优先
        return index>a.index;//最小值优先
    }
};

int main(){
    priority_queue<node>mypq[105];
    node a,tmp;
    int t,n,s,i,j,k;
    int fast,sid;
    scanf("%d",&t);
    for(i=1;i<=t;++i){
        scanf("%d",&n);
        for(j=1;j<=n;++j){
            scanf("%d%d",&a.f,&s);
            a.index=j;
            mypq[s].push(a);
        }
        printf("Case #%d:
",i);
        for(j=0;j<n;++j){//秒,1s出队1个
            fast=-1;sid=1;
            for(k=1;k<=100;++k){//速度s
                if(!mypq[k].empty()){
                    tmp=mypq[k].top();
                    if(tmp.f+k*j>fast){
                        fast=tmp.f+k*j;
                        sid=k;
                    }
                    else if(tmp.f+k*j==fast&&tmp.index<mypq[sid].top().index)
                        sid=k;
                }
            }
            printf("%d",mypq[sid].top().index);
            mypq[sid].pop();
            if(j<n-1)printf(" ");
        }
        printf("
");
    }
    return 0;
}
View Code
原文地址:https://www.cnblogs.com/gongpixin/p/4753906.html