POJ3304计算几何
http://poj.org/problem?id=3304
题意:实际上就是问有没有一条直线能与所有给定的线段有交点。
思路:用给定的线段的端点枚举所有可能的直线(要判断两条线段端点是不是重合),然后判断这个直线是不是与所有的线段有交点
判断直线与线段是否相交的方法:(就用上两篇博客中的判断一个点在一条直线的左边还是右边。)两个向量以点b为公共点,如果向量bg在向量ba的逆时针方向(左边),那么(g-b)*(a-b)<0(也就是上两篇说的x1*y2-x2*y1<0),再设点a(x1,x2),点b(x2,y2),点g(x,y),那么就有(x-x2)*(y1-y2)-(x1-x2)*(y-y2)<0;如果在右边就>0;所以如果直线与线段相交,那么一定有线段两端在直线左右,所以一个<0一个>0相乘必定小于0,问题解决。
AC代码:
#include<iostream> #include<cstdio> #include<cstring> #include<cstdlib> #include<algorithm> #include<cmath> using namespace std; #define EPS 1e-8 struct node { float x1,y1,x2,y2; }; node setting[110]; int n; float distance(float x1,float y1,float x2,float y2) { return sqrt((x1-x2)*(x1-x2)+(y1-y2)*(y1-y2)); } float corss(float x1,float y1,float x2,float y2,float x,float y) { return ((x-x2)*(y1-y2)-(x1-x2)*(y-y2)); } int judge(float x1,float y1,float x2,float y2) { if(distance(x1,y1,x2,y2)<EPS)return 0; for(int i=1;i<=n;i++) if(corss(x1,y1,x2,y2,setting[i].x1,setting[i].y1)* corss(x1,y1,x2,y2,setting[i].x2,setting[i].y2)>EPS) return 0; return 1; } int main() { int t; int ans; scanf("%d",&t); while(t--) { scanf("%d",&n); for(int i=1;i<=n;i++) { scanf("%f%f%f%f",&setting[i].x1,&setting[i].y1,&setting[i].x2,&setting[i].y2); } if(n==1) { printf("Yes!\n"); continue; } ans=0; for(int i=1;i<=n&&!ans;i++) for(int j=i+1;j<=n&&!ans;j++){ if(judge(setting[i].x1,setting[i].y1,setting[j].x1,setting[j].y1)|| judge(setting[i].x1,setting[i].y1,setting[j].x2,setting[j].y2)|| judge(setting[i].x2,setting[i].y2,setting[j].x1,setting[j].y1)|| judge(setting[i].x2,setting[i].y2,setting[j].x2,setting[j].y2)) ans=1; } if(ans)printf("Yes!\n"); else printf("No!\n"); } return 0; }

浙公网安备 33010602011771号