題目鏈接
可以看出是差分和前綴和(差分的話自己並不熟練),這題主要是對前面知識進行回顧了差分和前綴和的知識。
解題思路:
- 首先這個先利用差分來記錄每個點的值,這裏利用差分,然後類似於前綴和的形式來求出每個位置的值
- 然後我們利用前綴和(二維前綴和)
- 然後最終求出即可
這裏需要注意的是:(注意形式)
二維前綴和:
a[i][j] = a[i][j] + a[i - 1][j] + a[i][j - 1] - a[i - 1][j - 1];
求出結果:
a[x2][y2] - a[x1 - 1][y2] - a[x2][y1 - 1] + a[x1 - 1][y1 - 1];
代碼:
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
long long a[2010][2010];
int main(){
int n, m, k, q;
scanf("%d%d%d%d",&n,&m,&k,&q);
for (int i = 0; i < k; i ++){
int x1, y1, x2, y2;
scanf("%d%d%d%d",&x1,&y1,&x2,&y2);
a[x1][y1] += 1;
a[x2 + 1][y1] -= 1;
a[x1][y2 + 1] -= 1;
a[x2 + 1][y2 + 1] += 1;
}
// 差分完每一塊的值
for (int i = 1; i <= n; i++){
for (int j = 1; j <= m; j ++){
a[i][j] = a[i][j] + a[i - 1][j] + a[i][j - 1] - a[i - 1][j - 1];
}
}
// 前綴和
for (int i = 1; i <= n; i++){
for (int j = 1; j <= m; j ++){
a[i][j] = a[i][j] + a[i - 1][j] + a[i][j - 1] - a[i - 1][j - 1];
}
}
for (int i = 0 ; i < q; i ++){
int x1, y1, x2, y2;
scanf("%d%d%d%d",&x1,&y1,&x2,&y2);
printf("%lld\n",a[x2][y2] - a[x1 - 1][y2] - a[x2][y1 - 1] + a[x1 - 1][y1 - 1]);
}
return 0;
}