二维st表模板-求矩阵内的最大值or最小值
一、 算法思路:和一维st表完全一致,都是倍增+dp
二、与一维st表的区别:
维度不同,用矩阵合并
三、图像演示
预处理
大矩形由四种子矩阵合并而来
横向分割大矩阵
纵向分割大矩阵
查询
总之就是由小矩阵合并到到大矩阵。
#include<bits/stdc++.h>
using namespace std;
const int maxn=255,maxm=255;
int f[maxn][maxm][10][10],Log[maxn],n,m,t;
void init()
{
scanf("%d%d%d",&n,&m,&t);
for(int i=1;i<=n;++i)
for(int j=1;j<=m;++j)
scanf("%d",&f[i][j][0][0]);
Log[0]=-1;
for(int i=1;i<=max(n,m);++i) Log[i]=Log[i>>1]+1;
for(int k=0;k<=Log[n];++k)
{
for(int h=0;h<=Log[m];++h)
{
if(!k&&!h) continue;
for(int i=1;i+(1<<k)-1 <= n;++i)
{
for(int j=1;j+(1<<h)-1 <= m;++j)
{
if(k)
{
f[i][j][k][h]=max(f[i][j][k-1][h],f[i+(1<<(k-1))][j][k-1][h]);
}
else
{
f[i][j][k][h]=max(f[i][j][k][h-1],f[i][j+(1<<(h-1))][k][h-1]);
}
}
}
}
}
}
int main()
{
init();
int x,y,xx,yy,ans1,ans2,ans;
for(int i=1;i<=t;++i)
{
scanf("%d%d%d%d",&x,&y,&xx,&yy);
int k=Log[xx-x+1],h=Log[yy-y+1];
ans1=max(f[x][y][k][h],f[xx-(1<<k)+1][yy-(1<<h)+1][k][h]);
ans2=max(f[xx-(1<<k)+1][y][k][h],f[x][yy-(1<<h)+1][k][h]);
ans=max(ans1,ans2);
printf("%d\n",ans);
}
return 0;
}