二维偏序,利用二维前缀和的思想,一个矩阵(x1,y1,x2,y2)可以由(0,0,x2,y2)+(0,0,x1-1,x2-1)-(0,0,x1-1,y2)-(0,0,x2,y1-1)得出,所以按x轴排序,用树状数组记录y轴的(0,y]的值,然后就ok了。
此题有一个nc坑点,就是他让你计算的一个点的权值不是这个值在螺旋矩阵中的值,而是螺旋矩阵的值的每位数的和,列如5*5的螺旋矩阵在(3,3)为25,但是其实这个点的权值是7(2+5),而且样例因为都是个位数所以按权值和算完全符合!
螺旋矩阵给出坐标求出相应值的函数是copy的网上的模板。
#include
#include
#include
#include
using namespace std;
const int MAX_N=1e5+1000;
int n;
struct skt{
int x,y,sum;
}a[MAX_N];
struct kt{
int x,y,num;
int sum;
}b[4*MAX_N];
struct ssg{
int x1,y1,x2,y2;
int a,b,c,d;
}que[MAX_N];
bool cmp(skt a,skt b){
return a.x<b.x;
}
bool cmpp(kt a,kt b){
return a.x<b.x;
}
int sum[1010000];
void add(int p,long long x){
while(p<=n){
sum[p]+=x;
p+=p&-p;
}
}
int ask(int p){
int ans=0;
while(p){
ans+=sum[p];
p-=p&-p;
}
return ans;
}
long long asking(long long n,long long a,long long b){
long long q=min(min(a,b),min(n-a+1,n-b+1));
long long ans=0;
if(a<=b){
q--;
ans=4*(n-q)*q+a+b-2*(q+1)+1;
}
else
ans=4*(n-q)*q-a-b+2*q+1;
return ans;
}
int work(long long x){
int ans=0;
while(x){
ans+=x%10;
x=x/10;
}
return ans;
}
int main(void){
int T,m,q,i;
int x1,x2,y1,y2;
cin>>T;
while(T--){
scanf("%d%d%d",&n,&m,&q);
for(i=0;i<=n;i++)
sum[i]=0;
for(i=0;i<m;i++){
scanf("%d%d",&a[i].x,&a[i].y);
long long qx=n-a[i].x+1,qy=n-a[i].y+1;
long long N=n;
a[i].sum=work(asking(N,qx,qy));
//cout<
//cout<
}
sort(a,a+m,cmp);
for(i=0;i<q;i++){
scanf("%d%d%d%d",&x1,&y1,&x2,&y2);
que[i].x1=x1;que[i].y1=y1;que[i].x2=x2;que[i].y2=y2;
b[4*i].x=x1-1;b[4*i].y=y1-1;b[4*i].num=4*i;
b[4*i+1].x=x1-1;b[4*i+1].y=y2;b[4*i+1].num=4*i+1;
b[4*i+2].x=x2;b[4*i+2].y=y1-1;b[4*i+2].num=4*i+2;
b[4*i+3].x=x2;b[4*i+3].y=y2;b[4*i+3].num=4*i+3;
}
sort(b,b+4*q,cmpp);
int cnta=0,cntb=0;
a[m].x=1e9;b[4*q].x=1e9;
while(cnta<m||cntb<4*q){
//cout<
if(a[cnta].x<=b[cntb].x){
add(a[cnta].y,a[cnta].sum);
cnta++;
}
else{
b[cntb].sum=ask(b[cntb].y);
cntb++;
}
}
//cout<<"asdfa\n";
for(i=0;i<4*q;i++){
if(b[i].num%4==0)
que[b[i].num/4].a=b[i].sum;
else if(b[i].num%4==1)
que[b[i].num/4].b=b[i].sum;
else if(b[i].num%4==2)
que[b[i].num/4].c=b[i].sum;
else
que[b[i].num/4].d=b[i].sum;
}
for(i=0;i<q;i++){
int ans=que[i].a-que[i].b-que[i].c+que[i].d;
//cout<
printf("%d\n",ans);
}
}
return 0;
}