码迷,mamicode.com
首页 > 其他好文 > 详细

poj 2019 Cornfields(二维RMQ)

时间:2015-08-17 21:19:23      阅读:125      评论:0      收藏:0      [点我收藏+]

标签:

题意:N,B,K表示原矩阵为N*N,查询矩阵为B*B,K次查询;

        每次查询给出a,b,表示矩阵左上方的坐标为(a,b);求查询矩阵中最大值与最小值之差;

思路:二维RMQ,将dp的一三维看做第一维,二四维看做第二维;注意细节;

#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
int N,B,K;
int dpmax[255][255][8][8];
int dpmin[255][255][8][8];
int mm[255][255],num[255];
void init_rmq(int n,int m){
    for(int i=1;i<=n;i++){
        for(int j=1;j<=m;j++){
            dpmax[i][j][0][0]=mm[i][j];
            dpmin[i][j][0][0]=mm[i][j];
        }
    }
    for(int ii=0;ii<=num[n];ii++){
        for(int jj=0;jj<=num[m];jj++){
            if(ii+jj){  //细节
                for(int i=1;i+(1<<ii)-1<=n;i++){
                    for(int j=1;j+(1<<jj)-1<=m;j++){
                        if(ii){ //细节
                            dpmax[i][j][ii][jj]=max(dpmax[i][j][ii-1][jj],dpmax[i+(1<<(ii-1))][j][ii-1][jj]);
                            dpmin[i][j][ii][jj]=min(dpmin[i][j][ii-1][jj],dpmin[i+(1<<(ii-1))][j][ii-1][jj]);
                        }
                        else{
                            dpmax[i][j][ii][jj]=max(dpmax[i][j][ii][jj-1],dpmax[i][j+(1<<(jj-1))][ii][jj-1]);
                            dpmin[i][j][ii][jj]=min(dpmin[i][j][ii][jj-1],dpmin[i][j+(1<<(jj-1))][ii][jj-1]);
                        }
                    }
                }
            }
        }
    }
}
int rmqmax(int x1,int y1,int x2,int y2){
    int k1=num[x2-x1+1];
    int k2=num[y2-y1+1];
    x2=x2-(1<<k1)+1;
    y2=y2-(1<<k2)+1;
    return max(max(dpmax[x1][y1][k1][k2],dpmax[x1][y2][k1][k2]),max(dpmax[x2][y1][k1][k2],dpmax[x2][y2][k1][k2]));
}
int rmqmin(int x1,int y1,int x2,int y2){
    int k1=num[x2-x1+1];
    int k2=num[y2-y1+1];
    x2=x2-(1<<k1)+1;
    y2=y2-(1<<k2)+1;
    return min(min(dpmin[x1][y1][k1][k2],dpmin[x1][y2][k1][k2]),min(dpmin[x2][y1][k1][k2],dpmin[x2][y2][k1][k2]));
}
int main(){
    int i,j,k,a,b;
    num[0]=-1;
    for(i=1;i<=255;i++){
        num[i]=(i&(i-1))==0?num[i-1]+1:num[i-1];
    }
    while(scanf("%d%d%d",&N,&B,&K)!=EOF){
        for(i=1;i<=N;i++){
            for(j=1;j<=N;j++){
                scanf("%d",&mm[i][j]);
            }
        }
        init_rmq(N,N);
        while(K--){
            scanf("%d%d",&a,&b);
            int t1=rmqmax(a,b,a+B-1,b+B-1);
            int t2=rmqmin(a,b,a+B-1,b+B-1);
            printf("%d\n",t1-t2);
        }
    }
    return 0;
}

 

poj 2019 Cornfields(二维RMQ)

标签:

原文地址:http://www.cnblogs.com/dominatingdashuzhilin/p/4737511.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!