题意:第 i i i 只猫吃一条鱼需要花费 a [ i ] a[i] a[i]的时间。且一只猫在同一时间最多只会吃一条鱼。在第 0 0 0 时刻,每只猫会开始吃一条鱼。每当有一只猫吃完鱼时,如果此时还有鱼,它会立刻吃下一条鱼。如果有 k k k 只猫在同一时刻一起吃完了鱼,且此时剩下的鱼的个数 不足 k k k, a [ i ] a[i] a[i]较小的猫会优先吃鱼。 求 x x x 个时间后,有多少条鱼还没被吃过,以及有多少鱼已经被吃了一部分了。
考场上xjb YY的乱搞骗了70pts。
正解是用个小根堆,每次将鱼分给目前最先将要吃完的猫,让鱼的数量
−
1
-1
−1,直到时间已经超过
x
x
x或者所有鱼都被分配了,此时的
m
m
m就是剩下的鱼的数量。然后我们将堆中结束时间小于等于
x
x
x的弹出,堆中剩下的元素的数量就是已经被吃了一部分的。
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<queue>
#define ll long long
using namespace std;
priority_queue<pair<ll,int>,vector<pair<ll,int> >,greater<pair<ll,int> > >q;
int m,n,xx,a[1001000],ans;
int main()
{
cin>>m>>n>>xx;
for(int i=1;i<=n;++i)
{
scanf("%d",&a[i]);
q.push(make_pair(1ll*a[i],i));
}
m-=n;
while(m>=1&&q.top().first<xx)//这里是小于,因为当时间等于x时不会分配新的鱼
{
int x=q.top().first;
int y=q.top().second;
q.pop();
m--;
x+=a[y];
q.push(make_pair(x,y));
}
while(!q.empty()&&q.top().first<=xx)
q.pop();
while(!q.empty())
{
q.pop();
ans++;
}
cout<<m<<" "<<ans;
return 0;
}