http://poj.org/problem?id=1584
题意 给你个多边形和一个钉子,让你判断是否 钉子可以放里面
注意 1 ,多边形所给的顺序 可能是逆时针也可能时顺时针
2 ,钉子可能在多边形外面
3 ,钉子可能在多边形上
4 ,先给半径后给圆的坐标
#include<iostream> #include<cmath> #include<string> #include<algorithm> #include<queue> #include<cstring> #include<cstdio> using namespace std; const int N=1001; struct node { double x,y; }mem[N]; int Leftturn(double x1,double y1,double x2,double y2)//给出两个向量 求往哪转 { double ftemp=x1*y2-x2*y1; if(ftemp==0.0)//不转 return 0; if(ftemp>0.0)//左转 return 1; return -1;// 右转 } double Pegx,Pegy,Pegradius; bool Fit(int i,int j)//求点到线的距离 与半径比较 看是否合适 { double x1=mem[i].x-Pegx; double y1=mem[i].y-Pegy; double x2=mem[j].x-Pegx; double y2=mem[j].y-Pegy; double temp=fabs(x1*y2-y1*x2)/sqrt((mem[i].x-mem[j].x)*(mem[i].x-mem[j].x)+(mem[i].y-mem[j].y)*(mem[i].y-mem[j].y)); if(temp-Pegradius>=0.0) return true; return false; } int main() { int n; while(scanf("%d",&n)!=EOF) { if(n<3) break; scanf("%lf %lf %lf",&Pegradius,&Pegx,&Pegy); for(int i=1;i<=n;++i) { scanf("%lf %lf",&mem[i].x,&mem[i].y); } mem[0].x=mem[n].x; mem[0].y=mem[n].y; mem[n+1].x=mem[1].x; mem[n+1].y=mem[1].y; int i; for(i=0;i<n;++i) { if(Leftturn(mem[i+1].x-mem[i].x,mem[i+1].y-mem[i].y,mem[i+2].x-mem[i+1].x,mem[i+2].y-mem[i+1].y)<0) break; } int j; for(j=0;j<n;++j) { if(Leftturn(mem[j+1].x-mem[j].x,mem[j+1].y-mem[j].y,mem[j+2].x-mem[j+1].x,mem[j+2].y-mem[j+1].y)>0) break; } if(i<n&&j<n)//既存在左转 又存在右转 则一定突出 { printf("HOLE IS ILL-FORMED\n"); continue; } if(i<n&&j==n)//如果只有右转 没有左转 说明点的顺序是顺时针 应该颠倒过来 以便后面求解 { reverse(mem,mem+n+2); } for(i=0;i<n;++i) { if(Leftturn(Pegx-mem[i].x,Pegy-mem[i].y,mem[i+1].x-Pegx,mem[i+1].y-Pegy)>0)//点在三角形内部的话 则一定<=0 break; if(!Fit(i,i+1))//根据点到直线距离 和 圆半径的比较 看是否合适 break; } if(i<n) { printf("PEG WILL NOT FIT\n"); } else { printf("PEG WILL FIT\n"); } } return 0; }