POJ_1113_Wall_凸包

来源:互联网 发布:java web项目 打包jar 编辑:程序博客网 时间:2024/05/16 00:49

好久没有写题解了,也好久没刷题了,网赛打得一般,不过应该是可以出去了,得开始努力了!


题意:

给一个多边形,要求在它周围画一条包围它的闭合的线,使得线长度最短,同时要求线任意一点距离多边形不得小于l,求线长度,答案四舍五入到整数。


Input

The first line of the input file contains two integer numbers N and L separated by a space. N (3 <= N <= 1000) is the number of vertices in the King's castle, and L (1 <= L <= 1000) is the minimal number of feet that King allows for the wall to come close to the castle.

Next N lines describe coordinates of castle's vertices in a clockwise order. Each line contains two integer numbers Xi and Yi separated by a space (-10000 <= Xi, Yi <= 10000) that represent the coordinates of ith vertex. All vertices are different and the sides of the castle do not intersect anywhere except for vertices.

Output

Write to the output file the single number that represents the minimal possible length of the wall in feet that could be built around the castle to satisfy King's requirements. You must present the integer number of feet to the King, because the floating numbers are not invented yet. However, you must round the result in such a way, that it is accurate to 8 inches (1 foot is equal to 12 inches), since the King will not tolerate larger error in the estimates.

又是一道G++WA,C++A的题,POJ的G++版本是不是有问题。。。首先,对于一个直线,画的线必然是和它平行并且距离为l,如果在一个地方有凹进去的地方,虽然可以让我们画得线也凹进去,但是那样会增加长度,并且还要回到之后的点要求的位置,因此要求凸包,让线总是和凸包的边平行等长。对于凸包的顶点,用初中几何知识就可以知道画扇形圆弧最好,然后求一下扇形圆心角和,就可以把两部分加起来。

注意此凸包不应包括共线的中间点。


代码:

#include<iostream>#include<cstdio>#include<cstring>#include<string>#include<cmath>#include<algorithm>using namespace std;#define mxn 1010const double pi=acos(-1.0);int n;double l;struct point{double x,y;point(){}point(double _x,double _y){x=_x;y=_y;}bool operator < (const point& in)const{return x<in.x||x==in.x&&y<in.y;}point operator - (const point& in)const{return point(x-in.x,y-in.y);}}p[mxn];double cross(point p,point q){return p.x*q.y-p.y*q.x;}point hull[mxn];int convex_hull(){int cnt=0;sort(p,p+n);for(int i=0;i<n;++i){while(cnt>1&&cross(hull[cnt-1]-hull[cnt-2],p[i]-hull[cnt-2])<=0)--cnt;hull[cnt++]=p[i];}int tem=cnt;for(int i=n-2;i>=0;--i){while(cnt>tem&&cross(hull[cnt-1]-hull[cnt-2],p[i]-hull[cnt-2])<=0)--cnt;hull[cnt++]=p[i];}return cnt;}double dist(point p,point q){return sqrt((p.x-q.x)*(p.x-q.x)+(p.y-q.y)*(p.y-q.y));}int main(){while(scanf("%d%lf",&n,&l)!=EOF){for(int i=0;i<n;++i)scanf("%lf%lf",&p[i].x,&p[i].y);int num=convex_hull();double ans=0;for(int i=0;i<num-1;++i)ans+=dist(hull[i],hull[i+1]);ans+=2*pi*l;cout<<(int)ans<<endl;}return 0;}


0 0
原创粉丝点击