BZOJ1828: [Usaco2010 Mar]balloc 农场分配

n<=100000个房容量Ai,m<=100000头牛分别要占Li~Ri的房,求能同时满足的牛最多有多少。

先把这些各种各样要求的牛排个序观察一下,可以发现,如果若干头牛的Li是一样的,而Li处的容量不允许它们同时放,这时就要舍弃Ri大的那几头,因为价值相同,舍弃谁都不会影响当前的答案,但Ri大的对后面的牛可能产生阻碍。

这里所说的Li一样,其实可以更广泛地说,如果当前考虑的房中,前面的房满足要求,而这个房加入新牛后爆炸了,就应该把现在在房里的所有的牛中Ri大的那几头舍弃。

我们需要一个支持插入删除和查最大的结构——priority_queue!

ps:如果给每头牛加上权值,如何求权最大??

 1 #include<stdio.h>
 2 #include<string.h>
 3 #include<algorithm>
 4 #include<cstdlib>
 5 #include<queue>
 6 //#include<iostream>
 7 using namespace std;
 8 
 9 int n,m;
10 #define maxn 100011
11 int a[maxn],e[maxn];
12 struct segment
13 {
14     int l,r;
15     bool operator < (const segment &b) const {return l<b.l;}
16 }p[maxn];
17 priority_queue<int> que;
18 int x,y;
19 int main()
20 {
21     scanf("%d%d",&n,&m);
22     for (int i=1;i<=n;i++) scanf("%d",&a[i]);
23     memset(e,0,sizeof(e));
24     for (int i=1;i<=m;i++)
25     {
26         scanf("%d%d",&x,&y);
27         p[i].l=x;p[i].r=y;
28         e[x]++;e[y+1]--;
29     }
30     sort(p+1,p+1+m);
31     int now=0,j=1,ans=m;
32     for (int i=1;i<=n;i++)
33     {
34         now+=e[i];
35         while (j<=m && p[j].l==i) que.push(p[j++].r);
36         for (;now>a[i];now--)
37         {
38             e[que.top()+1]++;
39             que.pop();
40             ans--;
41         }
42     }
43     printf("%d\n",ans);
44     return 0;
45 }
View Code

 

posted @ 2017-07-21 10:58  Blue233333  阅读(165)  评论(0编辑  收藏  举报