[POJ 1819][Vjudge 18164] Disks [计算几何]

本文介绍了一种通过模拟解决圆排列问题的方法,该问题要求找出哪些圆不会影响两个挤压墙之间的最终距离。通过一系列计算确定了最左侧和最右侧圆的特殊处理方式,并给出了一段C++代码实现。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

现在有一列圆排在地平线上,用两个墙从左右向中间挤,问有哪些圆不会影响最终两个墙的距离

直接模拟做即可,另所有的圆尽量靠左,则在两相切的圆中间的那些不会影响最终两个墙的距离

最左边和最右边要特殊处理,最左边可以直接让圆不能超过左边的墙,最右边要判断,在圆的最右侧最靠右的圆里边的圆心最靠左的那个圆的右边的圆都是不会影响的


#include <cstdio>
#include <cstring>
#include <cmath>

const double eps=1e-9;

double r[1001];
double s[1001];
int last[1001];
int ans[1001];

int main() {
	int n,i,j,ansn=0,rr=0,ri=0;
	scanf("%d",&n);
	for (i=0;i<n;i++) {
		scanf("%lf",&r[i]);
		if (i==0) {
			s[i]=r[i];
			last[i]=-1;
		} else {
			j=0;
			s[i]=r[i];
			last[i]=-1;
			for (j=0;j<i;j++) {
				double tmp=s[j]+sqrt((r[i]+r[j])*(r[i]+r[j])-(r[i]-r[j])*(r[i]-r[j]));
				if (tmp-s[i]>eps) {
					s[i]=tmp;
					last[i]=j;
				}
			}
		}
		if (rr<s[i]+r[i]) {
			rr=s[i]+r[i];
			ri=i;
		}
		//printf("%d\n",last[i]);
	}
	for (i=n-1;i>ri;i--) {
		ans[ansn++]=i;
	}
	for (i=ri;i>=0;i=last[i]) {
		for (j=i-1;last[i]<j;j--) {
			ans[ansn++]=j;
		}
	}
	printf("%d\n",ansn);
	for (i=ansn-1;i>=0;i--) printf("%d\n",ans[i]+1);
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值