HDU 4456(二维树状数组+坐标转换)

题目链接:Problem - 4456

看别人叙述看的心烦,于是我自己画了一张图。

上图。

上代码

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <algorithm>
 4 #include <cstring>
 5 #include <cmath>
 6 using namespace std;
 7 const int maxn = 81111;
 8 const int maxm = 3e6+50; //这里大小的确定应该是80000*log2(20000)*log2(20000),算出来大约是一千三百万,数据应该是水一些,然而看所有人的题解,都是四百万,呵呵呵,这其中一定有什么交易。
 9 int p[maxn],x[maxn],y[maxn],z[maxn];
10 int arr[maxm];
11 int cnt[maxm];
12 int num = 0;
13 int len = 0;
14 int w = 0;
15 int lowbit(int x)
16 {
17     return x&(-x);
18 }
19 void pre(int x,int y)
20 {
21     for(int i=x;i<=w;i+=lowbit(i))
22     {
23         for(int j=y;j<=w;j+=lowbit(j))
24         {
25             cnt[num++] = i*w+j;
26         }
27     }
28 }
29 void sum(int x,int y,int tt)
30 {
31     for(int i=x;i<=w;i+=lowbit(i))
32     {
33         for(int j=y;j<=w;j+=lowbit(j))
34         {
35             int id = lower_bound(cnt,cnt+len,i*w+j)-cnt;
36             arr[id] += tt;
37         }
38     }
39 }
40 int getsum(int x,int y)
41 {
42     x=max(x,0); x=min(x,w); //边界
43     y=max(y,0); y=min(y,w);
44     int summ = 0;
45     for(int i=x;i>0;i-=lowbit(i))
46     {
47         for(int j=y;j>0;j-=lowbit(j))
48         {
49             int id = lower_bound(cnt,cnt+len,i*w+j)-cnt;
50             if(cnt[id]==(i*w+j)) summ += arr[id];
51         }
52     }
53     return summ;
54 }
55 int main()
56 {
57     int n,m;
58     while(scanf("%d",&n)!=EOF&&n)
59     {
60         scanf("%d",&m);
61         w = 2*n;
62         memset(cnt,0,sizeof(cnt));
63         memset(arr,0,sizeof(arr));
64         num = 0;
65         for(int i=1;i<=m;i++)
66         {
67             scanf("%d %d %d %d",&p[i],&x[i],&y[i],&z[i]);
68             int nx = x[i]-y[i]+n;
69             int ny = x[i]+y[i];
70             if(p[i]==1)
71             pre(nx,ny);
72         }
73         sort(cnt,cnt+num);
74         len = unique(cnt,cnt+num)-cnt;
75         for(int i=1;i<=m;i++)
76         {
77             int nx = x[i]-y[i]+n;
78             int ny = x[i]+y[i];
79             if(p[i]==1)
80             {
81                 sum(nx,ny,z[i]);
82             }
83             else
84             {
85                 int x1,y1,x2,y2,x3,y3,x4,y4;
86                 x1 = nx+z[i];y1 = ny+z[i];
87                 x2 = nx+z[i];y2 = ny-z[i];y2--;
88                 x3 = nx-z[i];y3 = ny+z[i];x3--;
89                 x4 = nx-z[i];y4 = ny-z[i];x4--;y4--;
90                 printf("%d\n",getsum(x1,y1)-getsum(x2,y2)-getsum(x3,y3)+getsum(x4,y4));
91             }
92         }
93     }
94     return 0;
95 }

 

posted @ 2016-08-11 21:10  卷珠帘  阅读(438)  评论(0编辑  收藏  举报