717 I. Cowboy Beblop at his computer
题意: 给定两个空间内的简单平面多边形,问两个多边形的边形成的环是否可以互相分离.
题解:
首先题面已经给出是否可以互相分离的判定方法是判断其中一个多边形穿过另一个多边时两种方向的次数是否一样.
然后考虑做法.求出一个多边形与另一个多边形所在平面的所有交点(忽略恰好相交但并没有穿过的点).如果没有交点,那么可以分离;否则有两个以上交点,可以确定经过这些交点的直线,求这条直线与另一个多边形的交点,对所有交点排序后可以判断多边形每条边是否穿过另一个多边形以及穿过的方向.
最后考虑计算:
记两个多边形的点分别为(P_{0,0},P_{0,1},cdots,P_{0,m_0-1})和(P_{1,0},P_{1,1},cdots,P_{1,n_1-1}).
先算出平面法向量(n_0=P_{0,0}P_{0,1} imes P_{0,0}P_{0,1},n_1=P_{1,0}P_{1,1} imes P_{1,0}P_{1,2}).判断两个平面是否平行或重合,等价于(n_0 imes n_1)是否为(0).如果平行或重合直接输出 "NO"
.
然后计算一个多边形的每条边穿过另外一个多边形所在平面时的交点以及方向.判断线段(P_{0,i}P_{0,i+1})是否与平面(P_{1,0}P_{1,1}P_{1,2})相交,等价于判断(n_1cdot P_{1,0}P_{0,i})和(n_1cdot P_{1,0}P_{0,i+1})是否符号相同.如果其中一个符号为0,那么我们可以看成线段穿过了平面半次.具体实现用两个符号相减即可表示线段穿过平面的情况.
判断相交后,还需要求出交点以排序.假设(P_{0,i}P_{0,i+1})与平面(P_{1,0}P_{1,1}P_{1,2})交于(X),并且设(P_{0,i}X=kP_{0,i}P_{0,i+1}).那么(P_{1,0}X=P_{1,0}P_{0,i}+kP_{0,i}P_{0,i+1}),两边与(n_1)点积,可得到(0=P_{1,0}P_{0,i}cdot n_1+kP_{0,i}P_{0,i+1}cdot n_1).算出(k)后即可得到(X)坐标.
最后,计算两平面交线方向与每个交点与(X)点积,即((n_1 imes n_2)cdot X),相当于点在该方向上的投影,可以用这个结果来代替坐标进行排序.
实现中一些奇怪的问题:计算最后的点积的范围理论上是坐标范围的(5)次方.但数据没卡用long long
可以过.使用double
反而会Time limit exceeded
.