poj 1113

来源:互联网 发布:java骰子游戏源码 编辑:程序博客网 时间:2024/06/12 20:10

      题目解法:实际上就是把所给的点构造出一个凸包,求出凸包的周长和以所给的最近距离为半径长度的圆的周长。构造凸包用的是Gram Scan(应该没拼错吧?我英语很烂的,原谅小弟)。

 

       以下是代码:

 

  1. #include "cstdio"#include "cmath"#include "algorithm"using namespace std;const int N=1005;const double eps=1e-8;const double Pi=3.1415926535;
  2. struct point{int x,y;}points[N],stack[N];int top;double dis(point a,point b){return sqrt((a.x-b.x)*(a.x-b.x)*1.0+(a.y-b.y)*(a.y-b.y));}
  3. double crossmulti(point p0,point p1,point p2){return (p1.x-p0.x)*(p2.y-p0.y)-(p2.x-p0.x)*(p1.y-p0.y);}
  4. bool cmp1(point p,point q){double k=crossmulti(points[0],p,q);if(k<-eps)return 0;else if(fabs(k)<eps && (dis(p,points[0])-dis(q,points[0]))>eps)return 0;else return 1;}
  5. bool cmp(point a,point b){if(a.x!=b.x) return a.y<b.y;else return a.x<b.x;}
  6. void cover_hull(int n){int i,k,d;int miny=points[0].y,index=0;sort(points,points+n,cmp);point temp;temp=points[index];points[index]=points[0];points[0]=temp;sort(points+1,points+n,cmp1);stack[0]=points[n-1];stack[1]=points[0];top=1;k=1;while(k<=n-1){double d=crossmulti(stack[top],stack[top-1],points[k]);if(d<=0){top++;stack[top]=points[k];k++;}else top--;}}
  7. int main(){int i,n,dist;double sum;scanf("%d%d",&n,&dist);for(i=0;i<n;i++)scanf("%d%d",&points[i].x,&points[i].y);cover_hull(n);sum=0;for(i=1;i<=top;i++)sum+=dis(stack[i-1],stack[i]);sum+=dis(stack[0],stack[top]);printf("%d/n",(int)(sum+2*Pi*dist+0.5));return 0;}

原创粉丝点击