Stacking Cylinders(poj2194)

Stacking Cylinders
Time Limit: 1000MS Memory Limit: 65536K
Total Submissions: 1188 Accepted: 623

Description

Cylinders (e.g. oil drums) (of radius 1 foot) are stacked in a rectangular bin. Each cylinder on an upper row rests on two cylinders in the row below. The cylinders in the bottom row rest on the floor. Each row has one less cylinder than the row below. 

This problem is to write a program to compute the location of the center of the top cylinder from the centers of the cylinders on the bottom row. Computations of intermediate values should use double precision. 

Input

Each data set will appear in one line of the input. An input line consists of the number, n, of cylinders on the bottom row followed by n floating point values giving the x coordinates of the centers of the cylinders (the y coordinates are all 1.0 since the cylinders are resting on the floor (y = 0.0)). The value of n will be between 1 and 10 (inclusive). The end of input is signaled by a value of n = 0. The distance between adjacent centers will be at least 2.0 (so the cylinders do not overlap) but no more than 3.4 (cylinders at level k will never touch cylinders at level k – 2).

Output

The output for each data set is a line containing the x coordinate of the topmost cylinder rounded to 4 decimal places, a space and the y coordinate of the topmost cylinder to 4 decimal places. Note: To help you check your work, the x-coordinate of the center of the top cylinder should be the average of the x-coordinates of the leftmost and rightmost bottom cylinders.

Sample Input

4 1.0 4.4 7.8 11.2
1 1.0
6 1.0 3.0 5.0 7.0 9.0 11.0
10 1.0 3.0 5.0 7.0 9.0 11.0 13.0 15.0 17.0 20.4
5 1.0 4.4 7.8 14.6 11.2
0

Sample Output

6.1000 4.1607
1.0000 1.0000
6.0000 9.6603
10.7000 15.9100
7.8000 5.2143

Source

[Submit]   [Go Back]   [Status]   [Discuss]



一种直观的思路,,两个底下的圆能确定它上一个圆的圆心

But how to do it?

两圆心相减,构造一向量,利用边长求出旋转角的正弦余弦,再用和角公式推一下旋转,,

#include<iostream>
#include<cstdio>
#include<queue>
#include<vector>
#include<bitset>
#include<algorithm>
#include<cstring>
#include<map>
#include<stack>
#include<set>
#include<cmath>
using namespace std;

typedef double DB;

struct Point{
	DB x,y;
	Point(DB _x = 0.00,DB _y = 0.00) {x = _x; y = _y;}
	Point operator - (const Point &b) {return Point(x - b.x,y - b.y);}
	bool operator < (const Point &b) const {return x < b.x;} 
}p[11];

typedef Point Vector;
int n;
DB two = 2.00;

DB Dot(Vector v1,Vector v2) {return v1.x*v2.x + v1.y*v2.y;}

Point Solve(Point p1,Point p2)
{
	Vector v = p2 - p1;
	DB L = sqrt(Dot(v,v)),LL = L/two;
	DB k = sqrt(two*two - LL*LL);
	DB cosalpha = LL/two,sinalpha = k/two;
	DB p = v.x*cosalpha - v.y*sinalpha;
	DB q = v.x*sinalpha + v.y*cosalpha; 
	return Point(p1.x + p*two/L,p1.y + q*two/L);
}

int main()
{
	#ifdef DMC
		freopen("DMC.txt","r",stdin);
	#endif
	
	for (int kk = 1; kk; kk++) {
		scanf("%d",&n); if (!n) break;
		for (int i = 1; i <= n; i++) {
			DB k; scanf("%lf",&k); 
			p[i] = Point(k,1.00);
		}
		sort(p + 1,p + n + 1);
		for (int i = n - 1; i; i--) 	
			for (int j = 1; j <= i; j++)
				p[j] = Solve(p[j],p[j+1]);
		printf("%.4lf %.4lf\n",p[1].x,p[1].y);
	}
	return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值