NYOJ1185
来自kuangbin模板
#include <bits/stdc++.h>
#define N 1010
#define mem(a,x) memset(a,x,sizeof a)
using namespace std;
#define INF 0x3f3f3f3f
const double eps = 1e-8;
typedef long long ll;
const int MAXN = 50010;
int dpmin[MAXN][20];
int dpmax[MAXN][20];
int mm[MAXN];
int mi[MAXN];
void initRMQ(int n,int b[]){
mm[0] = -1;
for(int i=1;i<=n;i++){
mm[i] = ((i&(i-1))== 0 )? mm[i-1]+1: mm[i-1];
dpmin[i][0] = dpmax[i][0] = b[i];
}
for(int j=1;j<=mm[n];j++)
for(int i=1;i+(1<<j)-1 <=n;i++){
dpmax[i][j] = max(dpmax[i][j-1] , dpmax[i+(1<<(j-1))][j-1]);
dpmin[i][j] = min(dpmin[i][j-1] , dpmin[i+(1<<(j-1))][j-1]);
}
}
int rmqmax(int x,int y){
int k = mm[y-x+1];
return max(dpmax[x][k], dpmax[y-(1<<k)+1][k]);
}
int rmqmin(int x,int y){
int k = mm[y-x+1];
return min(dpmin[x][k], dpmin[y-(1<<k)+1][k]);
}
int arr[MAXN];
int main(){
int n;
int t;scanf("%d",&t);
while(t--){
scanf("%d",&n);
for(int i=1;i<=n;i++) scanf("%d",&arr[i]);
initRMQ(n,arr);
int q;scanf("%d",&q);
while(q--){
int a,b,c;scanf("%d%d%d",&c,&a,&b);
if(c == 1)
printf("%d\n",rmqmin(a,b));
else if(c == 2)
printf("%d\n",rmqmax(a,b));
else
printf("%d\n",rmqmax(a,b)+rmqmin(a,b));
}
}
return 0;
}
二维RMQ模板
POJ2019
注意这里不要写错
((i & (i-1)) == 0)? 注意括号
mm[0] = -1;
for(int i=1;i<=500;i++)
mm[i] = ((i & (i-1)) == 0)? mm[i-1] + 1: mm[i-1];
#include <set>
#include <map>
#include <list>
#include <cmath>
#include <ctime>
#include <deque>
#include <queue>
#include <stack>
#include <cctype>
#include <cstdio>
#include <string>
#include <vector>
#include <cassert>
#include <cstdlib>
#include <cstring>
#include <sstream>
#include <iostream>
#include <algorithm>
#include <bitset>
#define PI acos(-1.0)
#define MOD 1000000009
#define INF 0x3f3f3f3f
#define Lowbit(x) (x & (-x))
#define mem(a,x) memset(a,x,sizeof(a))
#define Read() freopen("in.txt", "r", stdin);
#define Write() freopen("out.txt", "w", stdout);
#define bitnum(a) __builtin_popcount(a)
using namespace std;
#define INF 0x3f3f3f3f
const double eps = 1e-8;
typedef long long ll;
int val[310][310];
int mm[310]; // 二进制位数减一,使用前初始化
int dpmin[310][310][9][9];
int dpmax[310][310][9][9];
void initRMQ(int n,int m){
for(int i=1;i<=n;i++)
for(int j=1;j<=m;j++)
dpmin[i][j][0][0] = dpmax[i][j][0][0] = val[i][j];
for(int ii=0;ii<=mm[n];ii++)
for(int jj=0;jj<=mm[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){
dpmin[i][j][ii][jj] =
min(dpmin[i][j][ii-1][jj],
dpmin[i+(1<<(ii-1))][j][ii-1][jj]);
dpmax[i][j][ii][jj] =
max(dpmax[i][j][ii-1][jj],
dpmax[i+(1<<(ii-1))][j][ii-1][jj]);
}
else{
dpmin[i][j][ii][jj] =
min(dpmin[i][j][ii][jj-1],
dpmin[i][j+(1<<(jj-1))][ii][jj-1]);
dpmax[i][j][ii][jj] =
max(dpmax[i][j][ii][jj-1],
dpmax[i][j+(1<<(jj-1))][ii][jj-1]);
}
}
}
int rmqmax(int x1,int y1,int x2,int y2)
{
int k1 = mm[x2-x1+1];
int k2 = mm[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 = mm[x2-x1+1];
int k2 = mm[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(){
mm[0] = -1;
for(int i=1;i<=500;i++) //初始化mm
mm[i] = ((i & (i-1)) == 0)? mm[i-1] + 1: mm[i-1];
int N,B,K;
while(scanf("%d%d%d",&N,&B,&K) == 3){
for(int i=1;i<=N;i++)
for(int j=1;j<=N;j++)
scanf("%d",&val[i][j]);
initRMQ(N,N);
int x,y;
while(K--){
scanf("%d%d",&x,&y);
printf("%d\n",rmqmax(x,y,x+B-1,y+B-1) -
rmqmin(x,y,x+B-1,y+B-1));
}
}
}