POJ 3264 RMQ—ST

点击打开链接

题意:给出n个数的数列,m次询问,每次询问输出a~b的最大值与最小值之差

思路:用RMQ预处理,查询为O(1)的复杂度,很好的模版练习......,看的这篇博客学习的这一篇

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <iostream>
#include <algorithm>
using namespace std;
typedef long long ll;
const int inf=0x3f3f3f3f;
const int maxn=50010;
int max1[maxn][20],min1[maxn][20],num[maxn];
void RMQ_init(int n){
    for(int i=1;i<=n;i++)
        max1[i][0]=min1[i][0]=num[i];
    for(int i=1;(1<<i)<=n;i++){
        for(int j=1;j+(1<<i)-1<=n;j++){
            max1[j][i]=max(max1[j][i-1],max1[j+(1<<(i-1))][i-1]);
            min1[j][i]=min(min1[j][i-1],min1[j+(1<<(i-1))][i-1]);
        }
    }
}
int RMQ(int le,int ri){
    int k=0;
    while((1<<(k+1))<=ri-le+1) k++;
    int ans1=max(max1[le][k],max1[ri-(1<<k)+1][k]);
    int ans2=min(min1[le][k],min1[ri-(1<<k)+1][k]);
    return ans1-ans2;
}
int main(){
    int n,m;
    while(scanf("%d%d",&n,&m)!=-1){
        for(int i=1;i<=n;i++) scanf("%d",&num[i]);
        int le,ri;
        RMQ_init(n);
        for(int i=0;i<m;i++){
            scanf("%d%d",&le,&ri);
            printf("%d\n",RMQ(le,ri));
        }
    }
    return 0;
}





你可能感兴趣的:(数据结构,ACM,poj)