码迷,mamicode.com
首页 > 其他好文 > 详细

HDU #5283 Senior's Fish

时间:2016-08-16 23:37:44      阅读:274      评论:0      收藏:0      [点我收藏+]

标签:

题目描述:

平面上有一些鱼,初始时鱼会在一些位置,某些时刻编号在一段区间内的鱼会同时向x轴正方向,或y轴正方向平移一定距离,某些时刻会询问一个矩形内鱼的数量。

解题思路:

显然地,求一个矩形内的鱼可以用矩形四个顶点为右上角的整个左下矩形加加减减。那么问题就转化为一个顶点左下角矩形内鱼的数量。注意到鱼只会向右和向上的话,那就很好做。维护两颗线段树,分别维护编号在l~r的鱼的x坐标最大值、y坐标最大值。每次修改对应区间加。每次如果区间最大值大于限制,那就找出最大值的位置,赋为-inf,同时在树状数组删掉改点就可以了。询问就在树状数组上询问区间点的数量。

代码:

  1 #include <cstdio>
  2 #include <cstring>
  3 #include <algorithm>
  4 using namespace std;
  5 
  6 const int N = 3e4 + 10, inf = 1e9 + 1;
  7 int T, n, m, x1, y1, x2, y2, fis[N][2], ans[N], sum[N];
  8 
  9 struct que{int s, l, r, d;} q[N];
 10 
 11 struct node{int mx, tag;} tx[N * 8], ty[N * 8];
 12 
 13 int lowbit(int x) {return x & -x;}
 14 
 15 void add(int x, int v) {
 16     while (x <= N - 10) sum[x] += v, x += lowbit(x);
 17 }
 18 
 19 int Sum(int x) {
 20     int r = 0;
 21     while (x) r += sum[x], x -= lowbit(x);
 22     return r;
 23 }
 24 
 25 void buildx(int o, int l, int r) {
 26     if (l == r) {
 27         tx[o].mx = fis[l][0];
 28         tx[o].tag = 0;
 29         return;
 30     }
 31     int m = l + r >> 1;
 32     buildx(o << 1, l, m);
 33     buildx(o << 1 | 1, m + 1, r);
 34     tx[o].mx = max(tx[o << 1].mx, tx[o << 1 | 1].mx);
 35     tx[o].tag = 0;
 36 }
 37 
 38 void buildy(int o, int l, int r) {
 39     if (l == r) {
 40         ty[o].mx = fis[l][1];
 41         ty[o].tag = 0;
 42         return;
 43     }
 44     int m = l + r >> 1;
 45     buildy(o << 1, l, m);
 46     buildy(o << 1 | 1, m + 1, r);
 47     ty[o].mx = max(ty[o << 1].mx, ty[o << 1 | 1].mx);
 48     ty[o].tag = 0;
 49 }
 50 
 51 void pushdownx(int o) {
 52     if (!tx[o].tag) return;
 53     tx[o << 1].tag += tx[o].tag;
 54     tx[o << 1 | 1].tag += tx[o].tag;
 55     tx[o].mx += tx[o].tag;
 56     tx[o].tag = 0;
 57 }
 58 
 59 void pushdowny(int o) {
 60     if (!ty[o].tag) return;
 61     ty[o << 1].tag += ty[o].tag;
 62     ty[o << 1 | 1].tag += ty[o].tag;
 63     ty[o].mx += ty[o].tag;
 64     ty[o].tag = 0;
 65 }
 66 
 67 int queryx(int o, int l, int r) {
 68     if (l == r) return l;
 69     int m = l + r >> 1;
 70     pushdownx(o << 1);
 71     pushdownx(o << 1 | 1);
 72     if (tx[o << 1].mx > tx[o << 1 | 1].mx) return queryx(o << 1, l, m);
 73     return queryx(o << 1 | 1, m + 1, r);
 74 }
 75 
 76 int queryy(int o, int l, int r) {
 77     if (l == r) return l;
 78     int m = l + r >> 1;
 79     pushdowny(o << 1);
 80     pushdowny(o << 1 | 1);
 81     if (ty[o << 1].mx > ty[o << 1 | 1].mx) return queryy(o << 1, l, m);
 82     return queryy(o << 1 | 1, m + 1, r);
 83 }
 84 
 85 void changex(int o, int l, int r, int p, int v) {
 86     pushdownx(o);
 87     if (l == r) {
 88         tx[o].mx = v;
 89         return;
 90     }
 91     int m = l + r >> 1;
 92     if (p <= m) changex(o << 1, l, m, p, v);
 93     else changex(o << 1 | 1, m + 1, r, p, v);
 94     tx[o].mx = max(tx[o << 1].mx, tx[o << 1 | 1].mx);
 95 }
 96 
 97 void changey(int o, int l, int r, int p, int v) {
 98     pushdowny(o);
 99     if (l == r) {
100         ty[o].mx = v;
101         return;
102     }
103     int m = l + r >> 1;
104     if (p <= m) changey(o << 1, l, m, p, v);
105     else changey(o << 1 | 1, m + 1, r, p, v);
106     ty[o].mx = max(ty[o << 1].mx, ty[o << 1 | 1].mx);
107 }
108 
109 void updatax(int o, int l, int r) {
110     tx[o].mx = max(tx[o << 1].mx + tx[o << 1].tag, tx[o << 1 | 1].mx + tx[o << 1 | 1].tag);
111 }
112 
113 void modifyx(int o, int l, int r, int x, int y, int d) {
114     if (x <= l && r <= y) {
115         tx[o].tag += d;
116         return;
117     }
118     pushdownx(o);
119     int m = l + r >> 1;
120     if (x <= m) modifyx(o << 1, l, m, x, y, d);
121     if (y > m) modifyx(o << 1 | 1, m + 1, r, x, y, d);
122     updatax(o, l, r);
123 }
124 
125 void updatay(int o, int l, int r) {
126     ty[o].mx = max(ty[o << 1].mx + ty[o << 1].tag, ty[o << 1 | 1].mx + ty[o << 1 | 1].tag);
127 }
128 
129 void modifyy(int o, int l, int r, int x, int y, int d) {
130     if (x <= l && r <= y) {
131         ty[o].tag += d;
132         return;
133     }
134     pushdowny(o);
135     int m = l + r >> 1;
136     if (x <= m) modifyy(o << 1, l, m, x, y, d);
137     if (y > m) modifyy(o << 1 | 1, m + 1, r, x, y, d);
138     updatay(o, l, r);
139 }
140 
141 int work(int x, int y, int z) {
142     buildx(1, 1, n);
143     buildy(1, 1, n);
144     memset(sum, 0, sizeof sum);
145     for (int i = 1; i <= n; i ++) add(i, 1);
146     for (int i = 1; i <= m; i ++) {
147         while (tx[1].mx > x) {
148             int p = queryx(1, 1, n);
149             changex(1, 1, n, p, -inf);
150             if (Sum(p) - Sum(p - 1)) add(p, -1);
151         }
152         while (ty[1].mx > y) {
153             int p = queryy(1, 1, n);
154             changey(1, 1, n, p, -inf);
155             if (Sum(p) - Sum(p - 1)) add(p, -1);
156         }
157         if (q[i].s == 1) modifyx(1, 1, n, q[i].l, q[i].r, q[i].d);
158         if (q[i].s == 2) modifyy(1, 1, n, q[i].l, q[i].r, q[i].d);
159         if (q[i].s == 3) ans[i] += z * (Sum(q[i].r) - Sum(q[i].l - 1));
160     }
161 }
162 
163 int main() {
164     scanf("%d", &T);
165     while (T --) {
166         scanf("%d", &n);
167         scanf("%d %d %d %d", &x1, &y1, &x2, &y2);
168         for (int i = 1; i <= n; i ++) scanf("%d %d", &fis[i][0], &fis[i][1]);
169         scanf("%d", &m);
170         for (int i = 1; i <= m; i ++) {
171             scanf("%d %d %d", &q[i].s, &q[i].l, &q[i].r);
172             if (q[i].s != 3) scanf("%d", &q[i].d);
173         }
174         memset(ans, 0, sizeof ans);
175         work(x2, y2, 1), work(x1 - 1, y1 - 1, 1), work(x2, y1 - 1, -1), work(x1 - 1, y2, -1);
176         for (int i = 1; i <= m; i ++) if (q[i].s == 3)    printf("%d\n", ans[i]);
177     }
178     return 0;
179 }

 

HDU #5283 Senior's Fish

标签:

原文地址:http://www.cnblogs.com/awner/p/5778157.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!