codeforces 115E Linear Kingdom Races 线段树 + DP 好题
来源:互联网 发布:java 轮询查询数据库 编辑:程序博客网 时间:2024/06/05 10:30
参考了这里 http://blog.sina.com.cn/s/blog_6a6aa7830100x890.html
题意:有N条赛道,每一条初始时都是坏的,修复第i条赛道的费用是cost[i];赛道上会举办m个赛事,每个赛事会用到[L,R]之间的赛道,而且要保证赛事进行必须使得这一段的赛道完好,每项赛事还可以获得一定的钱数。问题要求安排哪些比赛可以使得收益最大。
可以设dp[i]表示到i这个赛道为止能获得最大的利益
有状态转移方程
dp[i]=max(dp[i-1],dp[j]+benefit[j+1][i]-mend[j+1][i]);
注: j+1->i之间有赛道
数据范围200000 暴力的话显然超时,所以可以考虑用某种数据结构优化一下,我用了线段树
做法:
先把m项赛事按右端点递增排个序,这样就可以将以同一个端点结束的赛事一起考虑,去更新前面的DP【】
一项赛事[L,R] 能影响的DP值肯定是在L之前的,即 dp【1~L-1】,要不然比赛场地都不完整,无法获利
还有就是每一次枚举到某段赛道i时,都要对前面所有的DP值 - cost[R],即dp[1~R-1]都减cost[R], 当我们选用所有的以同一个点结尾的赛道时,
dp[L-1]+benefit[L][R]-mend[L][R],获利之前必须先承受L+1~R这段路的维修费用
然后dp[1~L-1]都可以加上L - >R赛道带来的获利,所以给1->L-1这段的DP值加上benefit[L][R],
然后线段树还有一个作用就是查询这个区间的最大值,即更新之后最大的DP值Max[1]
dp[i]=max(dp[i-1],Max[1]);
然后将求得的DP值插入线段树中i位置即可
以下是代码
#include<cstdio>#include<cstring>#include<algorithm>using namespace std;#define lson L,R,val,l,m,x<<1#define rson L,R,val,m+1,r,x<<1|1typedef __int64 lld;const int maxn = 200010;struct seg{ int l,r; lld val; bool operator <(const seg &cmp) const{ return r<cmp.r; }}ss[maxn];int cost[maxn];lld dp[maxn],Max[maxn<<2],add[maxn<<2];lld max(lld a,lld b){ return a>b?a:b;}void pushup(int x){ Max[x]=max(Max[x<<1],Max[x<<1|1]);}void pushdown(int x){ if(add[x]){ add[x<<1]+=add[x]; add[x<<1|1]+=add[x]; Max[x<<1]+=add[x]; Max[x<<1|1]+=add[x]; add[x]=0; }}void update(int L,int R,lld val,int l,int r,int x){ if(L<=l&&r<=R){ add[x]+=val; Max[x]+=val; return ; } pushdown(x); int m=(l+r)>>1; if(L<=m) update(lson); if(R>m) update(rson); pushup(x);}int main(){ int n,m,i,j; while(scanf("%d%d",&n,&m)!=EOF) { for(i=1;i<=n;i++) scanf("%d",&cost[i]); for(i=0;i<m;i++) scanf("%d%d%I64d",&ss[i].l,&ss[i].r,&ss[i].val); sort(ss,ss+m); memset(add,0,sizeof(add)); memset(Max,0,sizeof(Max)); dp[0]=0; for(i=1,j=0;i<=n;i++) { update(0,i-1,-cost[i],0,n,1); while(ss[j].r==i&&j<m) { update(0,ss[j].l-1,ss[j].val,0,n,1); j++; } dp[i]=max(dp[i-1],Max[1]); update(i,i,dp[i],0,n,1); } printf("%I64d\n",dp[n]); } return 0;}
- codeforces 115E Linear Kingdom Races 线段树 + DP 好题
- CodeForces 115E Linear Kingdom Races(线段树 + DP)
- 【codeforces 115E】Linear Kingdom Races (datestructs(seg.tree)+dp)
- E. Linear Kingdom Races
- 【codeforces 115E】Linear Kingdom Races 题意&题解&代码(c++)
- Codeforces 675E Trains and Statistic【dp+线段树】好题!好题!
- Codeforces 474E Pillars【Dp+线段树+二分+离散化】好题~
- codeforces 474E Pillars(线段树+dp)
- Codeforces 474E Pillars dp+线段树
- Codeforces 474E Pillars dp+线段树
- Codeforces 834D The Bakery【Dp+线段树】好题~
- Codeforces 474E Pillars dp+线段树(水
- codeforces 271E 离散化+线段树,dp优化
- 【codeforces】480E Parking Lot 线段树+DP
- codeforces E. Trains and Statistic 线段树优化dp
- Codeforces Round #353 (Div. 2) E 线段树+dp
- codeforces 675-E Trains and Statistic 线段树+dp
- codeforces 777E dp+线段树+离散化
- poj 3334 计算几何
- codeforces 180D
- poj 1986 RMQ&&LCA( 模板题)
- codeforces 182D Common Divisors KMP做法
- codeforces 182E Wooden Fence 动态规划
- codeforces 115E Linear Kingdom Races 线段树 + DP 好题
- 后缀数组论文推荐题
- zoj zju 3597 Hit the Target! 线段树 扫描线
- zoj zju 3606 Lazy Salesgirl
- Ubuntu APT常用命令参数
- poj 3093 01背包
- codeforces ABBYY Cup 2.0
- codeforces 46D 线段树 区间合并
- CF 12D BALL 线段树 && 树状数组