RMQ 问题集合
题目描述
有一座延绵不断、跌宕起伏的山,最低处海拔为0,最高处海拔不超过8848米,从这座山的一端走到另一端的过程中,每走1米海拔就升高或降低1米。有Q个登山队计划在这座山的不同区段登山,当他们攀到各自区段的最高峰时,就会插上队旗。请你写一个程序找出他们插旗的高度。
注意,起点为0,所以n应该++一下,常数上,st表比线段树慢了大概5倍吧。
#include<bits/stdc++.h>
using namespace std;
const int maxn = 1005000;
int st[maxn][24];
int n;
void init()
{
for(int j = 1;(1<<j) <= n;j++){
for(int i = 1;i+(1<<j)-1 <= n;i++){
st[i][j] = max(st[i][j-1],st[i+(1<<(j-1))][j-1]);
}
}
}
int query(int l,int r){
int k = 0;
for(k = 0;(1<<(k+1))<=(r-l+1);k++);
return max(st[l][k],st[r-(1<<k)+1][k]);
}
int main()
{
freopen("climb.in","r",stdin);
freopen("climb.out","w",stdout);
scanf("%d",&n);
n++;
for(int i = 1;i <= n;i++) scanf("%d",&st[i][0]);
init();
int m;
scanf("%d",&m);
for(int i = 1;i <= m;i++){
int l,r;
scanf("%d%d",&l,&r);
l++;r++;
if(l > r) swap(l,r);
printf("%d\n",query(l,r));
}
return 0;
}

浙公网安备 33010602011771号