【有趣的有趣的家庭菜园】题解
来源:互联网 发布:华一软件 编辑:程序博客网 时间:2024/04/28 02:40
分析
设f[i]指1~i没有比i更高的草是,1~i的收益。
显然转移为,当h[j]<=h[i]
然后设g[i]指i~n没有比i更高的草是,i~n的收益。转移同上。答案就是max(f[i]+g[i]-p[i]),O(n^3),超时。
如何优化呢?由于n<=100000,就离散化h,以高度搞个有标记线段树,记录
#include <cmath>#include <iostream>#include <cstdio>#include <cstdlib>#include <cstring>#include <algorithm>#include <queue>const long long maxlongint=2147483647;using namespace std;long long tree[400000],f[200000],g[200000],n,m,ans,tot,h[200000],p[200000],c[200000],bef[200000],reh[200000],dee[400000];void q(long long l,long long r){ long long i=l,j=r,mid=reh[(l+r)/2],e; while(i<j) { while(reh[i]<mid) i++; while(reh[j]>mid) j--; if(i<=j) { e=reh[i]; reh[i]=reh[j]; reh[j]=e; e=bef[i]; bef[i]=bef[j]; bef[j]=e; i++; j--; } } if(i<r) q(i,r); if(l<j) q(l,j);}long long disc(){ long long k; q(1,n); k=0; for(long long i=1;i<=n;i++) { if(reh[i]!=reh[i-1]) k++; h[bef[i]]=k; }}long long find(long long v,long long l,long long r,long long x,long long y){ if(l==x && r==y) { return tree[v]; } if(tree[v*2]!=tree[0]) { tree[v*2]-=dee[v]; dee[v*2]+=dee[v]; } else { tree[v*2]=-dee[v]; dee[v*2]+=dee[v]; } if(tree[v*2+1]!=tree[0]) { tree[v*2+1]-=dee[v]; dee[v*2+1]+=dee[v]; } else { tree[v*2+1]=-dee[v]; dee[v*2+1]+=dee[v]; } dee[v]=0; long long mid=(l+r)/2,t,t1; if(y<=mid) { return find(v*2,l,mid,x,y); } else if(x>mid) return find(v*2+1,mid+1,r,x,y); else { return max(find(v*2,l,mid,x,mid),find(v*2+1,mid+1,r,mid+1,y)); } return t;}long long put(long long v,long long l,long long r,long long hi,long long pu){ if(l==r) { tree[v]=max(tree[v],pu); return 0; } if(tree[v*2]!=tree[0]) { tree[v*2]-=dee[v]; dee[v*2]+=dee[v]; } else { tree[v*2]=-dee[v]; dee[v*2]+=dee[v]; } if(tree[v*2+1]!=tree[0]) { tree[v*2+1]-=dee[v]; dee[v*2+1]+=dee[v]; } else { tree[v*2+1]=-dee[v]; dee[v*2+1]+=dee[v]; } dee[v]=0; long long mid=(l+r)/2; if(hi<=mid) { put(v*2,l,mid,hi,pu); tree[v]=max(tree[v*2+1],tree[v*2]); } else { put(v*2+1,mid+1,r,hi,pu); tree[v]=max(tree[v*2],tree[v*2+1]); } tree[v]=max(tree[v*2],tree[v*2+1]);}long long de(long long v,long long l,long long r,long long x,long long y,long long d){ if(l==x && r==y) { dee[v]+=d; tree[v]-=d; return 0; } if(tree[v*2]!=tree[0]) { tree[v*2]-=dee[v]; dee[v*2]+=dee[v]; } else { tree[v*2]=-dee[v]; dee[v*2]+=dee[v]; } if(tree[v*2+1]!=tree[0]) { tree[v*2+1]-=dee[v]; dee[v*2+1]+=dee[v]; } else { tree[v*2+1]=-dee[v]; dee[v*2+1]+=dee[v]; } dee[v]=0; long long mid=(l+r)/2; if(y<=mid) de(v*2,l,mid,x,y,d); else if(x>mid) de(v*2+1,mid+1,r,x,y,d); else de(v*2,l,mid,x,mid,d),de(v*2+1,mid+1,r,mid+1,y,d); tree[v]=max(tree[v*2],tree[v*2+1]); }int main(){ scanf("%lld\n",&n); long long i,j,k; for(i=1;i<=n;i++) { scanf("%lld%lld%lld\n",&reh[i],&p[i],&c[i]); bef[i]=i; } disc(); memset(tree,200,sizeof(tree)); put(1,0,n,0,0); memset(dee,0,sizeof(dee)); for(i=1;i<=n;i++) { f[i]=find(1,0,n,0,h[i])+p[i]; put(1,0,n,h[i],f[i]); de(1,0,n,0,h[i]-1,c[i]); } memset(tree,200,sizeof(tree)); put(1,0,n,0,0); memset(dee,0,sizeof(dee)); ans=0; for(i=n;i>=1;i--) { g[i]=find(1,0,n,0,h[i])+p[i]; put(1,0,n,h[i],g[i]); de(1,0,n,0,h[i]-1,c[i]); } for(i=1;i<=n;i++) ans=max(ans,f[i]-p[i]+g[i]); printf("%lld\n",ans);}
1 0
- 【有趣的有趣的家庭菜园】题解
- BZOJ4240: 有趣的家庭菜园
- 4240: 有趣的家庭菜园
- bzoj4240: 有趣的家庭菜园
- 有趣的有趣的家庭菜园
- [JZOJ4296]有趣的有趣的家庭菜园
- BZOJ 4240 有趣的家庭菜园
- ssoj2455有趣的有趣的家庭菜园(线段树)
- 【NOIP2015模拟11.2】有趣的有趣的家庭菜园
- 【NOIP模拟】有趣的有趣的家庭菜园
- 【NOIP2015模拟11.2】有趣的有趣的家庭菜园
- JOI 有趣的有趣的家庭菜园Fgarden
- 【NOIP模拟题】【线段树】【离散化】【DP】2016.11.14第三题 有趣的有趣的家庭菜园 题解
- bzoj 4240: 有趣的家庭菜园 树状数组
- [树状数组] BZOJ 4240 有趣的家庭菜园
- 【OI做题记录】【BZOJ】有趣的家庭菜园
- 树状数组——BZOJ4240 有趣的家庭菜园
- [BZOJ]4240: 有趣的家庭菜园 贪心+树状数组
- 改动已经存在数据的MySQL表结构
- 对象转json
- 树莓派
- Java中equals和==的区别
- 1005
- 【有趣的有趣的家庭菜园】题解
- 关于OC中block深究(对上次内容的补充)
- POJ 2485
- 通过jQuery Ajax使用FormData对象上传文件,Grails读取FormData数据
- Codeforces Round #345 (Div. 2) B. Beautiful Paintings __ greedy and Bucket_sort
- 8个排序算法的稳定性总结
- RedHat设置Yum源
- js jQuery 相关
- HDU4569-Special equations-小优化简单题