POJ1113 计算几何--整形凸包模板周长

来源:互联网 发布:黑客技术软件网盘 编辑:程序博客网 时间:2024/06/07 05:23

今天的主题是凸包!凸包!凸包!


G模板原地址:http://blog.csdn.net/nyist_tc_lyq/article/details/74776760 

5种凸包的解法思路:http://blog.csdn.net/bone_ace/article/details/46239187


这题嘛。。4个1/4圆+凸包周长,这城堡比较好,边都能转移出去


记得4舍5入

//求凸包的点#include<iostream>#include<math.h>#include<stdio.h>#include<algorithm>using namespace  std;const double PI = acos(-1.0);#define ll long long#define N 10005struct point{int x,y;point(){}point(int a,int b){x=a,y=b;}point operator -(const point &b)const{return point(x - b.x,y - b.y);}int operator ^(const point &b)const//叉积{return x*b.y - y*b.x;}int operator *(const point &b)const//点积{return x*b.x + y*b.y;     //绕原点旋转角度B(弧度值),后x,y的变化}} a[N],p[N];//p[]用来储存凸包   a数组存原来的点struct line{point s,e;line() {}line(point _s,point _e){s = _s;e = _e;}} lines[1005];int xmult(point p0,point p1,point p2) //计算p0p1 X p0p2{return (p1-p0)^(p2-p0);}int n,tot;//n为二维平面上点的个数,tot为凸包上点的个数int dis(point a,point b){return (a.x-b.x)*(a.x-b.x)+(a.y-b.y)*(a.y-b.y);}bool cmp(point p1,point p2)//极角排序;{int x=xmult(p1,p2,a[0]);if(x>0||(x==0&&dis(p1,a[0])<dis(p2,a[0]))) return 1;return 0;}bool cmp2(point p1,point p2){if(p1.x!=p2.x)return p1.x<p2.x;return p1.y<p2.y;}void Graham()  //O(nlogn){int k=0;for(int i=0; i<n; i++)if(a[i].y<a[k].y||(a[i].y==a[k].y&&a[i].x<a[k].x)) k=i;swap(a[0],a[k]);//找出左下角最小那个sort(a+1,a+n,cmp);//for(int i=0; i<n; i++)//{//cout<<"test:"<<i<<" "<<a[i].x<<" "<<a[i].y<<endl;//}tot=2,p[0]=a[0],p[1]=a[1];for(int i=2; i<n; i++){while(tot>1&&xmult(p[tot-1],p[tot-2],a[i])>=0) tot--;p[tot++]=a[i];}}int main(){double R;cin>>n>>R;for(int i=0; i<n; i++){int t1,t2;cin>>t1>>t2;a[i]=point(t1,t2);}Graham();//sort(p,p+tot,cmp2);//for(int i=0; i<tot; i++)//{//cout<<p[i].x<<" "<<p[i].y<<endl;//}double ans=PI*R*2.0;for(int i=0; i<tot-1; i++){ans+=sqrt((double)dis(p[i],p[i+1]));}ans+=sqrt((double)dis(p[0],p[tot-1]));int ans1=(int)(ans+0.5);cout<<ans1<<endl;}