For each test case, output the corresponding name of Alisha’s query, separated by a space.
Sample Input
1
5 2 3
Sorey 3
Rose 3
Maltran 3
Lailah 5
Mikleo 6
1 1
4 2
1 2 3
Sample Output
Sorey Lailah Rose
題目大意
Alisha要舉辦一個party,會有k個來賓,每一個來賓會有一個價值爲vi的禮物,可是Alisha不能同時接待這麼多人,因而她會分好幾回打開大門,放幾我的進來,題目會給出m對數,分別是t和p,即在第t我的到達後,打開大門,在外面排隊的前p我的進來。排隊的方式是根據禮物的價值從高到低排,價值同樣的先來的站前面。最後全部的人都會進來。最後給出q次查詢,詢問第幾個進來的人是誰。
好比題目中,Sorey先來,Alisha在第一我的來到以後,打開門放一我的進來,也就是Sorey。而後Rose、Maltran、Lailah都來了,由於Lailah的禮物貴重,因此他排在前面,Maltran的禮物和Rose同樣,排在Rose後面,如今Alisha開門放前兩我的進來,也就是Lailah和Rose。而後Mikleo拿着價值爲6的禮物站到了Maltran的前面,最後他們都進來了,因而進門的順序是:Sorey Lailah Rose Mikleo Maltran.對於三次查詢 輸出的是前三我的的名字。
分析
這個題目顯然是要採用優先隊列,可是我老是RE,以後看了別人的代碼才恍然大悟:題目給出的m對數,t不必定是按順序來的,也就是說樣例中的 1 1 和 4 2 是能夠反過來的!!因此不能在輸入的時候就完成模擬,這是我一直RE的緣由(原來RE也有多是這樣的.....小弱雞學到了)
代碼實現
#include<bits/stdc++.h>
using namespace std;
typedef struct node
{
int vul;
int num;
char names[205];
friend bool operator < (const node & a,const node & b)
{
return a.vul < b.vul || (a.vul == b.vul && a.num > b.num);
}
}vistor;
priority_queue <vistor> pq;
vistor v[150005];
int anss[150005],w[150005];
int main()
{
int t;
cin>>t;
while(t--)
{
memset(v,0,sizeof(v));
memset(anss,0,sizeof(anss));
memset(w,0,sizeof(w));
while(!pq.empty())
pq.pop();
int k,m,q,i,j,s=1,r=0,x,y;
scanf("%d%d%d",&k,&m,&q);
for(i=1;i<=k;i++)
{
scanf("%s",v[i].names);
scanf("%d",&v[i].vul);
v[i].num=i;
}
for(i=1;i<=m;i++)
{
scanf("%d %d",&x,&y);
w[x]+=y;
}
for(i=1;i<=k;i++)
{
pq.push(v[i]);
while(w[i]--)
{
if(!pq.empty())
{
anss[s++]=pq.top().num;
pq.pop();
}
}
}
while(!pq.empty())
{
anss[s++]=pq.top().num;
pq.pop();
}
for(i=1;i<=q;i++)
{
scanf("%d",&x);
if(i!=q)
printf("%s ",v[anss[x]].names);
else
printf("%s\n",v[anss[x]].names);
}
}
}