Cornfields
Time Limit:1000MS Memory Limit:30000KB 64bit IO Format:%I64d & %I64u
Description
给出一个N*N (N<=250)的方阵,以及K(<=100000)个询问。每次询问如下:以(Xi,Yi)为左上角,边长为B的子方阵中,最大值和最小值的差是多少?
注意对于所有的询问,B都是一个定值。
Input
第一行N,B(<=N),K。含义如上。
接下来N行N列的一个矩阵,每个数<=250。
接下来K行表示询问,每行两个数Xi, Yi 表示询问的方阵的左上角。
Output
一行一个正整数,含义如上。
Sample Input
5 3 1 5 1 2 6 3 1 3 5 2 7 7 2 4 6 1 9 9 8 6 5 0 6 9 3 9 1 2
Sample Output
5#include<cstring> #include<string> #include<iostream> #include<queue> #include<cstdio> #include<algorithm> #include<map> #include<cstdlib> #include<cmath> #include<vector> //#pragma comment(linker, "/STACK:1024000000,1024000000"); using namespace std; #define INF 0x3f3f3f3f #define maxn 255 int val[maxn][maxn]; int pos[maxn]; int dpmax[maxn][maxn][9][9]; int dpmin[maxn][maxn][9][9]; void initRMQ(int n,int m) { pos[0]=-1; for(int i=1; i<=n; i++) pos[i]=(i&i-1)==0?(pos[i-1]+1):pos[i-1]; for(int i=1; i<=n; i++) for(int j=1; j<=m; j++) dpmax[i][j][0][0]=val[i][j],dpmin[i][j][0][0]=val[i][j]; for(int ii=0; ii<=pos[n]; ii++) { for(int jj=0; jj<=pos[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 rmq(int x1,int y1,int x2,int y2) { int k1=pos[x2-x1+1]; int k2=pos[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]))- 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 n,b,k; while(scanf("%d%d%d",&n,&b,&k)!=EOF) { for(int i=1; i<=n; i++) { for(int j=1; j<=n; j++) { scanf("%d",&val[i][j]); } } initRMQ(n,n); while(k--) { int l,r; scanf("%d%d",&l,&r); int ans=rmq(l,r,l+b-1,r+b-1); printf("%d\n",ans); } } return 0; }