您的位置:首页 > 其它

POJ2504 Bounding box

2014-07-31 00:48 411 查看


Time Limit: 1000MS Memory Limit: 65536K
Total Submissions: 1370 Accepted: 567
Description
The Archeologists of the Current Millenium (ACM) now and then discover ancient artifacts located at vertices of regular polygons. The moving sand dunes of the desert render the excavations difficult and thus once three vertices
of a polygon are discovered there is a need to cover the entire polygon with protective fabric.
Input
Input contains multiple cases. Each case describes one polygon. It starts with an integer n <= 50, the number of vertices in the polygon, followed by three pairs of real numbers giving the x and y coordinates of three vertices
of the polygon. The numbers are separated by whitespace. The input ends with a n equal 0, this case should not be processed.

Output
For each line of input, output one line in the format shown below, giving the smallest area of a rectangle which can cover all the vertices of the polygon and whose sides are parallel to the x and y axes.

Sample Input
4
10.00000 0.00000
0.00000 -10.00000
-10.00000 0.00000
6
22.23086 0.42320
-4.87328 11.92822
1.76914 27.57680
23
156.71567 -13.63236
139.03195 -22.04236
137.96925 -11.70517
0

Sample Output
Polygon 1: 400.000
Polygon 2: 1056.172
Polygon 3: 397.673


模拟题
题意:样例第一行为一个正多边形的边数,2~4行是正多边形三个顶点的坐标,求一个能把该正多边形完全包裹最小的矩形的面积。
思路:通过正多边形的三个顶点求出该正多边形的外接圆,利用向量旋转公式由其中一个点开始求出正多边形所有点的坐标,能包裹住该正多边形的最小的矩形就是要找的矩形,求面积即可。

向量旋转公式:  xx=(xx1-x)*cos(t)-(yy1-y)*sin(t)+x;           yy=(xx1-x)*sin(t)+(yy1-y)*cos(t)+y

代码如下:

//Memory: 224K
//Time: 0MS

#include<iostream>
#include<cmath>
using namespace std;
int n;
double point[3][2];
double centre;
double pp[55][2];

double circle()
{
//求正多边形外接圆:两垂直平分线的交点就是圆心。
int i,j;
double x,y,k1,k2,b1,b2;
double pi=3.14159265,angle;
double middle1[2],middle2[2];
//求圆心,分斜率k是否存在是否为0.

//k1为0
if(point[0][1]==point[1][1])
{
x=(point[0][0]+point[1][0])/2;
//k2不存在
if(point[0][0]==point[2][0])
y=(point[0][1]+point[2][1])/2;
//k2存在且不为0
else
{
middle2[0]=(point[2][0]+point[0][0])/2;
middle2[1]=(point[2][1]+point[0][1])/2;
k2=(-1)/((point[2][1]-point[0][1])/(point[2][0]-point[0][0]));
b2=middle2[1]-k2*middle2[0];
y=k2*x+b2;
}
}
//k1不存在
else if(point[0][0]==point[1][0])
{
y=(point[0][1]+point[1][1])/2;
//k2为0
if(point[0][1]==point[2][1])
x=(point[0][0]+point[2][0])/2;
//k2存在且不为0
else
{
middle2[0]=(point[2][0]+point[0][0])/2;
middle2[1]=(point[2][1]+point[0][1])/2;
k2=(-1)/((point[2][1]-point[0][1])/(point[2][0]-point[0][0]));
b2=middle2[1]-k2*middle2[0];
x=(y-b2)/k2;
}
}
//k1存在且不为0
else
{
middle1[0]=(point[1][0]+point[0][0])/2;
middle1[1]=(point[1][1]+point[0][1])/2;
k1=(-1)/((point[1][1]-point[0][1])/(point[1][0]-point[0][0]));
b1=middle1[1]-k1*middle1[0];
//k2 =0
if(point[0][1]==point[2][1])
{
x=(point[0][0]+point[2][0])/2;
y=k1*x+b1;
}
//k2不存在
else if(point[0][0]==point[2][0])
{
y=(point[0][1]+point[2][1])/2;
x=(y-b1)/k1;
}
//k2存在且不为0
else
{
middle2[0]=(point[2][0]+point[0][0])/2;
middle2[1]=(point[2][1]+point[0][1])/2;
k2=(-1)/((point[2][1]-point[0][1])/(point[2][0]-point[0][0]));
b2=middle2[1]-k2*middle2[0];
x=(b2-b1)/(k1-k2);
y=k1*x+b1;
}
}
//点到圆心的距离即半径
double r=sqrt((point[0][0]-x)*(point[0][0]-x)+(point[0][1]-y)*(point[0][1]-y));
angle=(2*pi)/(double)n;
pp[0][0]=point[0][0];
pp[0][1]=point[0][1];
//通过向量旋转公式求出所有顶点
for(i=1;i<n;i++)
{
pp[i][0]=(pp[i-1][0]-x)*cos(angle)-(pp[i-1][1]-y)*sin(angle)+x;
pp[i][1]=(pp[i-1][0]-x)*sin(angle)+(pp[i-1][1]-y)*cos(angle)+y;
}
//找出xmax,xmin,ymax,ymin,确定矩形
double maxx=pp[0][0],minx=pp[0][0],maxy=pp[0][1],miny=pp[0][1],ss;
for(i=0;i<n;i++)
{
if(maxx<pp[i][0]) maxx=pp[i][0];
if(minx>pp[i][0]) minx=pp[i][0];
if(maxy<pp[i][1]) maxy=pp[i][1];
if(miny>pp[i][1]) miny=pp[i][1];
}
//求面积
ss=(maxx-minx)*(maxy-miny);
return ss;//返回面积
}

int main()
{
int i;
double area;
int num=1;
//多样例输入
while(cin>>n&&n)
{
if(n<3) continue;
for(i=0;i<3;i++)
cin>>point[i][0]>>point[i][1];
if(point[0][0]==point[1][0]&&point[1][0]==point[2][0]) continue;
if(point[0][1]==point[1][1]&&point[1][1]==point[2][1]) continue;
double aa=(point[2][1]-point[0][1])/(point[2][0]-point[0][0]);
double bb=(point[1][1]-point[0][1])/(point[1][0]-point[0][0]);
if(aa==bb) continue;
area=circle();
printf("Polygon %d: %.3lf\n",num++,area);
}
return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  map acm poj