POJ 1151 Atlantis 矩阵的并 线段树维护有效值
2012-09-20 17:54
337 查看
题意:给定n(n <=100)个矩形的左下角和右上角的坐标(0<=x y<=100000),求覆盖的面积。
题解:把所有的从坐标离散化,横向将所有垂直的线段排序并标记是矩形的左边还是右边线段,扫描时线段树维护有效的长度,累加得到答案。
Sure原创,转载请注明出处。
题解:把所有的从坐标离散化,横向将所有垂直的线段排序并标记是矩形的左边还是右边线段,扫描时线段树维护有效的长度,累加得到答案。
Sure原创,转载请注明出处。
#include <iostream> #include <cstdio> #include <memory.h> #include <algorithm> using namespace std; const int maxn = 102; struct line { double x,down,up; int left; bool operator < (const line &other) const { return x < other.x; } }vertical_line[maxn << 1]; struct node { int l,r; int lazy; double len; }seg[maxn << 3]; double yy[maxn << 1]; int n,top,cas = 0; void read() { double x1,x2,y1,y2; for(int i=0;i<n;i++) { scanf("%lf %lf %lf %lf",&x1,&y1,&x2,&y2); vertical_line[i].x = x1; vertical_line[i].down = y1; vertical_line[i].up = y2; vertical_line[i].left = 1; yy[i] = y1; vertical_line[i+n].x = x2; vertical_line[i+n].down = y1; vertical_line[i+n].up = y2; vertical_line[i+n].left = -1; yy[i+n] = y2; } sort(vertical_line ,vertical_line + 2 * n); sort(yy , yy + 2 * n); top = unique(yy , yy + 2 * n) - yy; return; } void biuld(int l,int r,int num) { seg[num].l = l; seg[num].r = r; seg[num].lazy = 0; seg[num].len = 0.0; if(l + 1 == r) return; int mid = (l + r) >> 1; biuld(l , mid , num << 1); biuld(mid , r , num << 1 | 1); return; } void UP(int num) { if(seg[num].lazy > 0) { seg[num].len = yy[seg[num].r] - yy[seg[num].l]; } else if(seg[num].l + 1 == seg[num].r) { seg[num].len = 0.0; } else { seg[num].len = seg[num << 1].len + seg[num << 1 | 1].len; } return; } void DOWN(int num) { if(seg[num].lazy > 0 && seg[num].l + 1 < seg[num].r) { seg[num << 1].lazy += seg[num].lazy; seg[num << 1 | 1].lazy += seg[num].lazy; seg[num].lazy = 0; seg[num << 1].len = yy[seg[num << 1].r] - yy[seg[num << 1].l]; seg[num << 1 | 1].len = yy[seg[num << 1 | 1].r] - yy[seg[num << 1 | 1].l]; } return; } void update(int l,int r,int num,int val) { if(l == seg[num].l && r == seg[num].r && val + seg[num].lazy >= 0) { seg[num].lazy += val; UP(num); return; } DOWN(num); int mid = (seg[num].l + seg[num].r) >> 1; if(mid >= r) update(l , r , num << 1 , val); else if(l >= mid) update(l , r , num << 1 | 1 , val); else { update(l , mid , num << 1 , val); update(mid , r , num << 1 | 1 , val); } UP(num); return; } void addline(int i) { int bjd = lower_bound(yy , yy + top , vertical_line[i].down) - yy; int bju = lower_bound(yy , yy + top , vertical_line[i].up) - yy; update(bjd , bju , 1 , vertical_line[i].left); return; } void solve() { double ans = 0.0; addline(0); for(int i=1;i<2*n;i++) { ans += seg[1].len * (vertical_line[i].x - vertical_line[i-1].x); addline(i); } printf("Test case #%d\n",++cas); printf("Total explored area: %.2f\n\n",ans); return; } int main() { while(~scanf("%d",&n) && n) { read(); biuld(0,top-1,1); solve(); } return 0; }
相关文章推荐
- poj 1151 Atlantis “线段树维护关键值”+“离散化”+“扫描线法”
- [poj 1151] Atlantis:扫描线+线段树求面积并
- POJ 1151 Atlantis(重叠矩阵面积和=离散化)
- hdu 1542&&poj 1151 Atlantis[线段树+扫描线求矩形面积的并]
- Poj 1151 Atlantis - 线段树
- POJ 1151 Atlantis(线段树离散化求面积并)(C++)
- POJ 1151 Atlantis(线段树+扫描线+坐标离散求矩形面积并)
- HDOJ 1542 (POJ 1151) Atlantis 【线段树 离散化 扫描线 面积并】
- POJ 1151 Atlantis(线段树扫描线)
- POJ-1151-Atlantis(线段树+扫描线+离散化)[矩形面积并]
- poj-1151-Atlantis-线段树求面积并
- poj 1151 Atlantis / hdu 1542 线段树扫描线 矩形面积并
- poj 1151-Atlantis线段树求矩形面积并解题报告
- POJ 1151 Atlantis 线段树/矩形面积并
- POJ 1151 Atlantis (线段树求矩形面积并)
- POJ 1151 Atlantis(扫描线 + 线段树 矩形面积的并)
- POJ 1151 Atlantis(扫描线,线段树)
- POJ 1151 Atlantis 线段树扫描线
- POJ 1151 Atlantis 线段树面积并
- HDU 1542 & POJ 1151 Atlantis【线段树扫描线】