传送门:poj1151
poj最近又炸了
(翻译什么的就算了,看看数据范围和样例就差不多了)
分析
标准的面积并,离散化一波直接求,注意是实数
代码
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <queue>
#define IL inline
using namespace std;
struct node
{
node *lch, *rch;
double len;
int cnt;
IL node()
{
lch = rch = 0;
len = 0;
cnt = 0;
}
} *root;
struct segment
{
double x, y1, y2;
int k;
IL segment(double x_ = 0, double y1_ = 0, double y2_ = 0, int k_ = 0)
{
x = x_; y1 = y1_; y2 = y2_; k = k_;
}
friend bool operator < (const segment &a, const segment &b)
{
return a.x < b.x;
}
}seg[205];
double num[205];
queue<node *>Q;
IL void del(node *p)
{
if(!p) return ;
del(p->lch); del(p->rch);
Q.push(p);
}
IL node* newnode()
{
if(Q.empty()) return new node;
node *p = Q.front(); Q.pop();
p->lch = p->rch = 0;
p->len = 0; p->cnt = 0;
return p;
}
IL void pushup(node *p, int l, int r)
{
if(p->cnt > 0)
p->len = num[r + 1] - num[l];
else
p->len = (l == r ? 0 : p->lch->len + p->rch->len);
}
IL void build(node *p, int l, int r)
{
if(l == r) return ;
int mid = (l + r) >> 1;
p->lch = newnode(); build(p->lch, l, mid);
p->rch = newnode(); build(p->rch, mid + 1, r);
}
IL void update(node *p, int l, int r, int x, int y, int k)
{
if(l == x && r == y)
{
p->cnt += k;
pushup(p, l, r);
return ;
}
int mid = (l + r) >> 1;
if(y <= mid) update(p->lch, l, mid, x, y, k); else
if(mid < x) update(p->rch, mid + 1, r, x, y, k); else
{
update(p->lch, l, mid, x, mid, k);
update(p->rch, mid + 1, r, mid + 1, y, k);
}
pushup(p, l, r);
}
int main()
{
for(int n, m, T = 1; scanf("%d", &n); ++T)
{
if(!n) break;
m = 0;
del(root);
for(int i = 1, k = 0; i <= n; ++i)
{
double x1, x2, y1, y2;
scanf("%lf %lf %lf %lf", &x1, &y1, &x2, &y2);
seg[++k] = segment(x1, y1, y2, 1); seg[++k] = segment(x2, y1, y2, -1);
num[++m] = y1; num[++m] = y2;
}
n <<= 1;
sort(seg + 1, seg + n + 1);
sort(num + 1, num + m + 1);
m = unique(num + 1, num + m + 1) - (num + 1);
root = newnode();
build(root, 1, m - 1);
double ans = 0;
for(int i = 1, y1, y2; i <= n; ++i)
{
ans += (seg[i].x - seg[i - 1].x) * root->len;
y1 = lower_bound(num + 1, num + m + 1, seg[i].y1) - num;
y2 = lower_bound(num + 1, num + m + 1, seg[i].y2) - num - 1;
update(root, 1, m - 1, y1, y2, seg[i].k);
}
printf("Test case #%d\nTotal explored area: %.2lf\n\n", T, ans);
}
return 0;
}