[BZOJ 1588][HNOI2002]营业额统计
2015-08-04 14:06
309 查看
1533. [HNOI2002]营业额统计
★★ 输入文件:turnover.in输出文件:
turnover.out简单对比
时间限制:5 s 内存限制:162 MB
【题目描述】
Tiger最近被公司升任为营业部经理,他上任后接受公司交给的第一项任务便是统计并分析公司成立以来的营业情况。Tiger拿出了公司的账本,账本上记录了公司成立以来每天的营业额。分析营业情况是一项相当复杂的工作。由于节假日,大减价或者是其他情况的时候,营业额会出现一定的波动,当然一定的波动是能够接受的,但是在某些时候营业额突变得很高或是很低,这就证明公司此时的经营状况出现了问题。经济管理学上定义了一种最小波动值来衡量这种情况:
该天的最小波动值=min{|该天以前某一天的营业额-该天营业额|}。
当最小波动值越大时,就说明营业情况越不稳定。
而分析整个公司的从成立到现在营业情况是否稳定,只需要把每一天的最小波动值加起来就可以了。你的任务就是编写一个程序帮助Tiger来计算这一个值。
第一天的最小波动值为第一天的营业额。
【输入格式】
第一行为正整数n(n<=32767),表示该公司从成立一直到现在的天数,接下来的n行每行有一个正整数ai(ai<=1000000),表示第i天公司的营业额。
【输出格式】
输出文件仅有一个正整数,即Sigma(每天最小的波动值) 。结果小于2^31 。
【样例输入】
6 5 1 2 5 4 6
【样例输出】
12
【提示】
结果说明:5+|1-5|+|2-1|+|5-5|+|4-5|+|6-5|=5+4+1+0+1+1=12
【来源】
HNOI 2002.搞了半天的inf问题,难道真的是模板不好么。。喵。
#include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #define maxn 50000 #include<cmath> using namespace std; struct Tree{ int l,r,val,key; #define l(x) tree[x].l #define r(x) tree[x].r #define val(x) tree[x].val #define key(x) tree[x].key }tree[maxn]; int tot,n,root,ans,num; const int inf=0x7fffffff; int Newnode(int t){ ++tot;val(tot)=t; key(tot)=(rand()<<15|rand())&0x7fffffff; return tot; } int Zig(int x){//left up int y=l(x);l(x)=r(y);r(y)=x; return y; } int Zag(int x){//right up int y=r(x);r(x)=l(y);l(y)=x; return y; } int Insert(int x,int t){ if(t<val(x))l(x)= !l(x)?Newnode(t):Insert(l(x),t); else r(x)= !r(x)?Newnode(t):Insert(r(x),t); if(key(x)>key(l(x)))x=Zig(x); else if(key(x)>key(r(x)))x=Zag(x); return x; } int Pre(int x){ int now=root,ans=-10000000; while(now){ if(val(now)<=x)ans=max(ans,val(now)),now=r(now); else now=l(now); } return ans; } int Suc(int x){ int now=root,ans=10000000; while(now){ if(val(now)>=x)ans=min(ans,val(now)),now=l(now); else now=r(now); } return ans; } void Init(){ key(0)=inf; scanf("%d%d",&n,&num); ans=num; root=Newnode(-inf); root=Insert(root,inf); root=Insert(root,num); } int Abs(int a){return a<0?-a:a;} int main(){ Init(); for(int i=2;i<=n;i++){ if(scanf("%d",&num)==EOF)num=0; ans+=min(Abs(num-Pre(num)),Abs(num-Suc(num))); root=Insert(root,num); } printf("%d",ans); return 0; }
嗯,Splay的插入,旋转还有待练习
1.注意mark
2.注意新建节点时的边要连好
3.注意一字形,之字形,和只有两个的情况
#include<iostream> #include<cstdio> #include<cstring> #include<algorithm> #define maxn 50000 using namespace std; int n,a[maxn]; struct Tree{ int ch[2],val,fa; #define fa(x) tree[x].fa #define val(x) tree[x].val #define c(x,y) tree[x].ch[y] }tree[maxn]; int ans,root,tot; void Rotate(int &p,int &x){ int mark= p==c(x,1),y=c(p,mark^1),z=fa(x); if(x==c(z,0))c(z,0)=p; if(x==c(z,1))c(z,1)=p; if(y)fa(y)=x; fa(p)=z;c(p,mark^1)=x;fa(x)=p;c(x,mark)=y; } void Splay(int p){ while(fa(p)){ int x=fa(p),y=fa(x); if(y==0)Rotate(p,x); else if(p==c(x,0)^x==c(y,0))Rotate(p,x),Rotate(p,y); else Rotate(x,y),Rotate(p,x); }root=p; } void Insert(int t){ int now=root,fa=root; while(now){ fa=now; if(t<=val(now))now=c(now,0); else now=c(now,1); }++tot;val(tot)=t;fa(tot)=fa; if(fa) if(t<=val(fa))c(fa,0)=tot; else c(fa,1)=tot; Splay(tot); } int Pre(int k){ int now=root,fa=root,ans=-0x7fffffff/3; while(now){ fa=now; if(k<val(now))now=c(now,0); else ans=max(ans,val(now)),now=c(now,1); }Splay(fa); return ans; } int Suf(int k){ int now=root,fa=root,ans=0x7fffffff/3; while(now){ fa=now; if(k<=val(now))ans=min(ans,val(now)),now=c(now,0); else now=c(now,1); }Splay(fa); return ans; } int main(){ scanf("%d",&n); scanf("%d",&ans); a[1]=ans; Insert(ans); for(int i=2;i<=n;i++){ if(scanf("%d",&a[i])==EOF)a[i]=0; ans+=min(abs(a[i]-Pre(a[i])),abs(a[i]-Suf(a[i]))); Insert(a[i]); }printf("%d",ans); return 0; }
相关文章推荐
- eclipse bookmark的使用
- if-else优化
- flash插入的方式(IE8以上兼容)
- JS数学表达式运算
- python练习题(三)
- FZU 2183 简单题
- Android SDK Manager国内下载缓慢的问题
- 解决VMware10虚拟机客户机操作系统无苹果MacOSX
- 002--spring配置详解
- U盘插拔监听 ,安装app监听,需要添加DataScheme
- iOS开发之窗口和视图
- HDU--2795 Billboard
- 客户端如何调用
- IDEA 加入注解~
- PrintArea打印,@media screen解决移动web开发的多分辨率问题,@media print设置打印的样式
- AngularJS中文介绍
- Linux下如何防止大量IP的并发访问(DDos)
- 抽象类,接口,内部类,包
- 在java中读取文件中的内容
- 查看mysql数据库大小、表大小和最后修改时间