POJ--1113[Wall] 凸包周长+圆的周长

 

题目大意:

给你N个点的坐标和一个距离限制L,让你求出1.包含所有点,2.且不能小于L;的最小周长。

 

思路分析:

其实就是凸包周长+圆的周长。。。。(直接套模版)。。。1A.。。。

 

感想:

做几何题模版很重要。。。。(平时多收集)。。。不过最重要的是自己理解。。。。

 

 

CODE:

/*计算几何:凸包周长+圆的周长*/
/*AC代码:32ms*/
#include <iostream>
#include <algorithm>
#include <cmath>
#define PI 3.14159265
#define MAXN 1005
using namespace std;
/*==================================================*\
| Graham 求凸包 O(N * logN)
| CALL: nr = graham(pnt, int n, res); res[]为凸包点集;
\*==================================================*/
struct point {double x,y;};
struct point pnt[MAXN],res[MAXN];
bool mult(point sp,point ep,point op)
{
	return (sp.x-op.x)*(ep.y-op.y)>=(ep.x-op.x)*(sp.y-op.y);
}
bool operator<(const point &l,const point &r)
{
	return l.y<r.y||(l.y==r.y&&l.x<r.x);
}
int graham(point pnt[],int n,point res[])//注意都是从0开始存
{
	int i,len,k=0,top=1;
	sort(pnt,pnt+n);
	if (n == 0) return 0; res[0]=pnt[0];
	if (n == 1) return 1; res[1]=pnt[1];
	if (n == 2) return 2; res[2]=pnt[2];
	for(i=2;i<n;i++)
	{
		while(top&&mult(pnt[i],res[top],res[top-1]))
			top--;
		res[++top]=pnt[i];
	}
	len=top;res[++top]=pnt[n-2];
	for(i=n-3;i>=0;i--)
	{
		while(top!=len&&mult(pnt[i],res[top],res[top-1]))
			top--;
		res[++top]=pnt[i];
	}
	return top;       // 返回凸包中点的个数
}
//----------------------------------------------------------//
double get_dis(point p1,point p2)
{return sqrt((double)((p1.x-p2.x)*(p1.x-p2.x)+(p1.y-p2.y)*(p1.y-p2.y)));}
int main()
{
	int i,j,N,L;
	while(scanf("%d%d",&N,&L)!=EOF)
	{
		for(i=0;i<N;i++)
			scanf("%lf%lf",&pnt[i].x,&pnt[i].y);
		int m=graham(pnt,N,res);
		double ans=0;
		for(i=0;i<m-1;i++)
			ans+=get_dis(res[i],res[i+1]);
		ans+=get_dis(res[m-1],res[0]);
		ans+=2*PI*L;
		int temp=(int)(ans*1000)%1000;
		if(temp>=500)
			printf("%d\n",(int)ans+1);
		else
			printf("%d\n",(int)ans); 
	}
	return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

__简言

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值