hdu5261

来源:互联网 发布:象形字典软件 编辑:程序博客网 时间:2024/06/04 18:45

蜀道难

Time Limit: 6000/3000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 375    Accepted Submission(s): 118


Problem Description
度度熊最近去四川游玩了一趟,在西南边,它发现了一个神奇的地方,那里有数不清的山,山脚的路组成了一个完美的圆,而山均匀的坐落在这个圆上。“此乃造物者之无尽藏也”,它大发诗情的感慨道。

山高皆不一,度度熊现在很想知道,距离最远的两座山顶是哪两座山。由于山顶不能直接到达,从一座山顶到另一座山顶的唯一方法是,先下山,沿着山脚的圆走到另一个山脚,再上山。当然,在山脚可以选择任意方向行走。
 

Input
第一行一个整数T,表示T组数据。

每组数据的第一行包含两个整数N(2N100000)R(1R109),表示山的个数和圆的半径。注意这里圆的半径不是R,而是NR/2PI (PI=3.1415926…) 。

接着的一行包括N个整数Hi(1Hi<=109),表示山峰的高度。
 

Output
对第i组数据,输出

Case #i:

然后输出两座山峰的ID (从1开始),如果有多组答案,输出字典序最小的一对。
 

Sample Input
23 11 1 15 21 10 1 10 10
 

Sample Output
Case #1:1 2Case #2:2 4
 

思路:相当于求h[j]+h[i]+(j-i)*r (i<j,j-i<=n/2),由于是圆圈的我们把数组扩增成原来的两倍,然后我们用一个长度为n/2的队列维护,队列头部存放离当前点距离最远的点,并用另一个队列存放最远点的 高度-位置*半径, 队列头部最远且下标最小,后面的距离点未必比头部小但下标比较大

#pragma comment(linker, "/STACK:1024000000,1024000000") #include<cstdio>#include<cstring>#include<algorithm>#include<stdlib.h>#include<vector>#include<stack>#include<queue>#include<map>#include<string>#include<cmath>#include<iostream>#include<deque>using namespace std;#define LL long long#define ULL unsigned long longconst int maxn = 100005;int num[maxn*2];deque<int> Q;deque<LL> QS;int n,r,ti=1,t;int main(void){scanf("%d",&t);LL ans;int ax,ay;int tx,ty;while(t--){ans = 0;printf("Case #%d:\n",ti++);scanf("%d%d",&n,&r);for(int i=1;i<=n;i++)scanf("%d",&num[i]),num[i+n]=num[i];while(!Q.empty()) Q.pop_back(),QS.pop_back();for(int i=1;i<=2*n;i++){while(!Q.empty()&&(i-Q.front())*2>n)  //使长度保持n/2 Q.pop_front(),QS.pop_front();if(!Q.empty()&&(i-Q.front())*2<=n&&1LL*num[i]+1LL*r*i+QS.front()>=ans){tx = Q.front();ty = i;if(tx>n) tx-=n;if(ty>n) ty-=n;if(tx>ty) tx=tx^ty,ty=tx^ty,tx=tx^ty;if(1LL*num[i]+1LL*r*i+QS.front()>ans)ax = tx,ay=ty,ans = 1LL*num[i]+1LL*r*i+QS.front();else if(tx<ax||(tx==ax&&ty<ay)) ax=tx,ay=ty;}LL now = num[i]-1LL*r*i;while(!Q.empty()&&now>QS.back())  //使末尾肯定是下标最大的,除去比当前点下标小且距离没当前点远的点 Q.pop_back(),QS.pop_back();Q.push_back(i);QS.push_back(now);}printf("%d %d\n",ax,ay);}return 0;}



0 0