半平面交模板

bzoj 2618

//%std
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
inline int read()
{
	int out = 0, fh = 1;
	char jp = getchar();
	while ((jp > '9' || jp < '0') && jp != '-')
		jp = getchar();
	if (jp == '-')
		fh = -1, jp = getchar();
	while (jp >= '0' && jp <= '9')
		out = out * 10 + jp - '0', jp = getchar();
	return out * fh;
}
void print(int x)
{
	if (x >= 10)
		print(x / 10);
	putchar('0' + x % 10);
}
void write(int x, char c)
{
	if (x < 0)
		putchar('-'), x = -x;
	print(x);
	putchar(c);
}
struct v2
{
	double x, y;
	v2 operator + (const v2 &rhs) const
	{
		return (v2){x + rhs.x, y + rhs.y};
	}
	v2 operator - (const v2 &rhs) const
	{
		return (v2){x - rhs.x, y - rhs.y};
	}
	double operator * (const v2 &rhs) const
	{
		return x * rhs.y - y * rhs.x;
	}
	v2 operator * (const double &lambda) const
	{
		return (v2){x * lambda, y * lambda};
	}
	double angle()
	{
		return atan2(y, x);
	}
};
struct Line
{
	v2 p, v;
	double angle()
	{
		return v.angle();
	}
	friend bool operator < (Line a, Line b) 
	{
		if (a.angle() != b.angle()) 
			return a.angle() < b.angle();
		return a.v * b.v < 0;
	}
};
v2 Inter(Line a, Line b)
{
	v2 u = a.p - b.p;
	double t = (b.v * u) / (a.v * b.v);
	return a.p + a.v * t;
}
bool Onleft(Line L, v2 p)
{
	return L.v * (p - L.p) > 0;
}
const int N = 500 + 10;
v2 p[N], poly[N];
Line q[N], L[N];
int n, head = 1, tail = 0;
double Hpi()
{
	sort(L + 1, L + 1 + n);
	q[++tail] = L[1];
	for (int i = 2; i <= n; ++i) if (L[i].angle() != L[i - 1].angle())
	{
		if (head < tail)
		{
			if (q[head].v * q[head + 1].v == 0)
				return 0;
			if (q[tail].v * q[tail - 1].v == 0)
				return 0;
		}
		while (head < tail && !Onleft(L[i], p[tail - 1]))
			--tail;
		while (head < tail && !Onleft(L[i], p[head]))
			++head;
		q[++tail] = L[i];
		if (head < tail)
			p[tail - 1] = Inter(q[tail - 1], q[tail]);
	}
	while (head < tail && !Onleft(q[head], p[tail - 1]))
		--tail;
	while (head < tail && !Onleft[q[tail], p[head]])
		++head;
	p[tail] = Inter(q[tail], q[head]);
	p[tail + 1] = p[head];
	if (tail - head + 1 <= 2)
		return 0.0;	
	double s = 0;
	for (int i = head; i <= tail; ++i)
		s += p[i] * p[i + 1];
	return fabs(s) / 2;
}
int main()
{
	int t = read();
	for (int i = 1; i <= t; ++i)
	{
		int k = read();
		for (int j = 1; j <= k; ++j)
			poly[j].x = read(), poly[j].y = read();
		poly[k + 1] = poly[1];
		for (int j = 1; j <= k; ++j)
		{
			++n;
			L[n].p = poly[j];
			L[n].v = poly[j + 1] - poly[j];
		}
	}
	printf("%.3lf\n", Hpi());
	return 0;
}

posted @ 2019-08-05 14:57  jklover  阅读(200)  评论(0编辑  收藏  举报