poj 1113 graham模板(水平序)

这题不多说,裸的模板,graham扫描算法,通过栈比较当前point与栈顶的两个point是否满足左转的关系,不满足时退栈直到栈空或这满足时。上代码:

/*
Memory: 180 KB        Time: 16 MS
Language: C++        Result: Accepted
By coolwind
*/
#include <math.h>
#include <stdio.h>
#include <string.h>
#include <algorithm>
using namespace std;
#define  MAXN 2000
const double Pi = acos(-1.0);
struct Point{
    int x;
    int y;
    Point (int a = 0, int b = 0):x(a),y(b){}
}point[MAXN];

int cmpxy(Point a, Point b)
{
    if(a.y == b.y)
        return a.x < b.x;
    return a.y < b.y;
}

int Xmul(Point a, Point b, Point o)
{
    return (a.x - o.x) * (b.y - o.y) - (a.y - o.y) * (b.x - o.x);
 }

double dis(Point a, Point b)
{
    return sqrt(1.0*((a.x - b.x) * (a.x - b.x) + (a.y - b.y) * (a.y - b.y)));
}

Point stack[MAXN];
int top;
double Graham(int n, int l)
{
    int i;
    top = 0;
    sort(point,point + n, cmpxy);
    stack[0] = point[0];
    stack[1] = point[1];
    top = 1;
    for(i = 2; i < n ; i ++)
    {
        while(top > 0 && Xmul(stack[top],stack[top - 1],point[i]) > 0)
            top --;
        stack[++top] = point[i];
    }
    
    int len = top;
    stack[++top] = point[n - 1];
    
    for(i = n - 2; i >= 0; i --)
    {
        while(top > len && Xmul(stack[top],stack[top - 1],point[i]) > 0)
            top --;
        stack[++top] = point[i];
    }
    
    double res = 0;
    for(i = 0; i < top; i ++)
        res += dis(stack[i],stack[i + 1]);
    res += l * 2.0 * Pi;
    
    return res;
}

int main()
{
    int n,l;
    int i;
    while(scanf("%d%d",&n,&l) != EOF)
    {
        for(i = 0 ; i < n ; i ++)
            scanf("%d%d",&point[i].x,&point[i].y);
        double res = Graham(n,l);
        printf("%.0lf\n",res);
    }
    return 0;
}
View Code

 

posted @ 2013-08-26 21:16  oucacm  阅读(164)  评论(0)    收藏  举报