luogu P4515 [COCI2009-2010#6] XOR 容斥

LINK:XOR

一个不常见的容斥套路题。

以往是只求三角形面积的交 现在需要求被奇数次覆盖的区域的面积。

打住 求三角形面积的交我也不会写 不过这道题的三角形非常特殊 等腰直角 且直角点都在左下方 这就有很多的性质了。

容易发现最后交出的三角形为等腰直角三角形。

考虑如何求若干个三角形交出的面积 不太会证明 题解区的一个神仙给出了一个式子。

(c_i=x_i+y_i+z_i)最终交出的三角形的直角边边长为 (MAX(0,min(c_i)-max(x_i)-max(y_i)))

数据范围这么小 显然可以子集容斥 不过对于枚举到的三角形 需要配上一定的容斥系数满足 偶消奇不消。

对于一个集合s来说 容斥系数为(2^{|S|-1}(-1)^{|S|-1})

怎么说 这是 对于这种容斥的常用套路(系数。

证明:(sum_{k=1}^nC(n,k)2^{k-1}(-1)^{k-1}=[![2|n]])

(sum_{k=1}^nC(n,k)(-2)^{k-1}=frac{sum_{k=1}^nC(n,k)(-2)^{k}}{-2}=frac{-1+sum_{k=0}^nC(n,k)(-2)^{k}}{-2})

二项式定理合并起来 可得(frac{1-(-2+1)^n}{2}=frac{1-(-1)^n}{2}=[![2|n]])

const int MAXN=12;
int n;
struct wy
{
	int x,y,r,w;
}t[MAXN];
db ans;
inline void dfs(int v,int sz,int z,int x,int y,int op)
{
	if(v==n+1)
	{
		if(!sz)return;
		ans=ans+(1ll<<sz-1)*op*((z-x-y)<0?0:(ll)(z-x-y)*(z-x-y));
		return;
	}
	dfs(v+1,sz+1,min(z,t[v].w),max(x,t[v].x),max(y,t[v].y),-op);
	dfs(v+1,sz,z,x,y,op);
}
int main()
{
	freopen("1.in","r",stdin);
	get(n);
	rep(1,n,i)
	{
		int x,y,z;
		get(x);get(y);get(z);
		t[i]=(wy){x,y,z};
		t[i].w=x+y+z;
	}
	dfs(1,0,INF,0,0,-1);
	printf("%.1lf",ans/2);
	return 0;
}
原文地址:https://www.cnblogs.com/chdy/p/13152209.html