BZOJ2093[Poi2010] Frog
来源:互联网 发布:打淘宝客服要话费吗 编辑:程序博客网 时间:2024/05/01 19:39
BZOJ2093[Poi2010] Frog
Description
一个条河无限宽,上面有n块石头,石头离左边的河岸(无限宽,右边河岸不晓得在哪)距离严格递增,现在Zxl想锻炼自己的跳跃能力(谁叫他在班里外号是鸟怪。。畸形),他在某一块石头上,想跳到离他这块石头第k远的石头上去,假如离他第k远的石头不是唯一的,他就选离岸最近的那一个(不然回不去了),他想你让他知道,从每块石头开始跳了m次后,自己在哪。
Input
第一行有3个由空格隔开的整数n, k (n, k <= 1,000,000), m (m <= 10^18)。
第二行有n个正整数,第i个数表示第i块石头离左岸的距离,保证输入的n个正整数严格递增,并且不超过10^18。
Output
一行n个由空格隔开的整数,第i个表示Zxl从第i块石头开始跳,跳m次后会在哪个石头上。
Sample Input
5 2 4
1 2 4 7 10
Sample Output
1 1 3 1 1
Solution:
自己对倍增的想法掌握的还不是很扎实啊…
首先,我们为什么要想到倍增:跳跃
既然想到用倍增求解后,问题就只剩下一个内容了:如何求离一个点第k近的点。
最开始想的就是二分,二分一个左端点,直接检验右端点是否可以,但是这样写起来效果并不好,代码很恶心。
#include<stdio.h>#include<ctype.h>#include<iostream>#define M 1000005#define ll long longusing namespace std;int d[2][M],ans[M];ll A[M];int min(int a,int b){return a<b?a:b;}inline void Rd(ll &res){ char c;res=0; while(c=getchar(),!isdigit(c)); do{ res=(res<<1)+(res<<3)+(c^48); }while(c=getchar(),isdigit(c));}int main(){ int n,k,sz=0;ll m; scanf("%d %d",&n,&k);cin>>m; for(int i=1;i<=n;i++)Rd(A[i]); for(int i=1;i<=n;i++){ int L=0,R=min(i-1,k),res; while(L<=R){ int mid=(L+R)>>1; if(i+k-mid>n){ L=mid+1; continue; } if(i+k-mid<n&&A[i+k-mid+1]-A[i]<A[i]-A[i-mid]){ R=mid-1; continue; } if(i-mid>1&&A[i]-A[i-mid-1]<=A[i+k-mid]-A[i]){ L=mid+1; continue; } res=mid; break; } d[0][i]=(A[i]-A[i-res]>=A[i+k-res]-A[i]?i-res:i+k-res); } int cur=0; for(int i=1;i<=n;i++)ans[i]=i; while(m){ if(m&1){ for(int i=1;i<=n;i++) ans[i]=d[cur][ans[i]]; } for(int i=1;i<=n;i++) d[!cur][i]=d[cur][d[cur][i]]; m>>=1,cur=!cur; } for(int i=1;i<=n;i++) printf("%d%c",ans[i],i==n?'\n':' '); return 0;}
然后大犇给出了
我们要求的内容是关于一个点的左边的一个端点与右边的一个端点(并且这两个端点之间的距离是确定的),于是我们就在单调性上研究研究。可以发现的是,这两个端点只会向右延伸,于是直接向右边一直移动指针过去就可以了。
int L=1,R=k+1; d[0][1]=k+1; for(int i=2;i<=n;i++){ while(R<n&&L<i&&A[R+1]-A[i]<A[i]-A[L])R++,L++; d[0][i]=(A[i]-A[L]>=A[R]-A[i]?L:R); }
- bzoj2093【POI2010】Frog
- BZOJ2093 [Poi2010]Frog
- BZOJ2093: [Poi2010]Frog
- BZOJ2093[Poi2010] Frog
- 2093: [Poi2010]Frog 倍增
- 2093: [Poi2010]Frog
- bzoj 2093: [Poi2010]Frog 倍增
- POI2010 Antisymmetry
- POI2010 Beads
- POI2010 Hamsters
- POI2010 Blocks
- POI2010 Hamsters
- Poi2010 Railway
- POI2010 题解
- [Poi2010]Antisymmetry
- [Poi2010]Antisymmetry
- Frog CMS
- hdu2182 Frog
- |洛谷|动态规划|P1156 垃圾陷阱
- framebuffer简介与应用
- Cache-Control no-cache与max-age=0的区别
- 机器学习笔记(十五)——HMM序列问题和维特比算法
- HDU 2031 进制转换
- BZOJ2093[Poi2010] Frog
- 【Maven实战】05 依赖
- Java笔试面试题二(常考问答)
- Linux下的shell编程(五)--循环
- Flask web的学习——一个简单的web结构
- HDU-2028Lowest Common Multiple Plus
- fzu 2020 组合数取模
- CDOJ 1292 卿学姐种花(暴力,分块,线段树)
- HDU 2588(欧拉函数的应用)