#include
#include
#include
typedef struct CPoint
{
double x, y;
}Point;
const int MAXSIZE = 10000;
const double EPS = 1E-6;
int stack[MAXSIZE];
int top;
Point p[MAXSIZE];
void GrahamScan(const int &n);
double Dist(const Point &arg1, const Point &arg2);
double Length(const int &n);
double Area(const int &n);
void Swap(const int &i, const int &j);
double Multi(const Point &p0, const Point &p1, const Point &p2);
int cmp(const void *arg1, const void *arg2);
int main(void)
{
int n;
while( scanf("%d", &n), n )
{
int i;
for( i=0; i < n; ++i )
{
scanf("%lf %lf", &p[i].x, &p[i].y);
}
if( n == 1 )
{
printf("周长: 0.00\t面积: 0.00\n");
}
else if( n == 2 )
{
printf("周长: %.2lf\t面积: 0.00\n", Dist(p[0], p[1]));
}
else
{
GrahamScan(n);
printf("周长: %.2lf\t面积: %.2lf\n", Length(top+1), Area(top+1));
}
}
return 0;
}
double Length(const int &n)
{
double sum = Dist( p[stack[n-1]], p[stack[0]] );
for( int i = 0; i < n-1; ++i )
{
sum += Dist( p[stack[i]], p[stack[i+1]] );
}
return sum;
}
double Area(const int &n)
{
double area = 0;
for( int i=0; i < n-1; ++i )
{
area += (p[stack[i]].x*p[stack[i+1]].y) - (p[stack[i+1]].x*p[stack[i]].y);
}
area = fabs(area) / 2;
return area;
}
double Dist(const Point &arg1, const Point &arg2)
{
return sqrt( (arg1.x - arg2.x)*(arg1.x - arg2.x) + (arg1.y - arg2.y)*(arg1.y - arg2.y) );
}
void Swap(const int &i, const int &j)
{
Point temp = p[i];
p[i] = p[j];
p[j] = temp;
}
double Multi(const Point &p0, const Point &p1, const Point &p2)
{
return (p1.x-p0.x)*(p2.y-p0.y) - (p2.x-p0.x)*(p1.y-p0.y);
}
int cmp(const void *arg1, const void *arg2)
{
Point a = *(Point*)arg1;
Point b = *(Point*)arg2;
double k = Multi(p[0], a, b);
if( k < -EPS ) return 1;
else if( fabs(k) < EPS && (Dist(a, p[0]) - Dist(b, p[0])) > EPS ) return 1;
else return -1;
}
void GrahamScan(const int &n)
{
int i, u = 0;
for( i = 1; i < n; ++i )
{
if( ( p[i].y < p[u].y ) || ( p[i].y == p[u].y && p[i].x < p[u].x ) ) u = i;
}
i = 0;
Swap(i, u);
qsort( p+1, n-1, sizeof(p[0]), cmp );
stack[0] = 0; stack[1] = 1; stack[2] = 2;
top = 2;
for( int j = 3; j < n; ++j )
{
while( Multi( p[j], p[stack[top]], p[stack[top-1]] ) > 0 )
{
--top;
if( top == 0 ) break;
}
stack[++top] = j;
}
}
//凸包题目:
凸包的基本应用
凸包拓展
用凸包求最远点对
提高题目: