HDU1392Surround the Trees(凸包判断 + 求周长)

http://www.cnblogs.com/hmhard/archive/2013/02/05/2893035.html 这是判断三角区域那块写的不好。

判断凸包的方法:

1、将所有点按照y从小到大排序,x从小到大排序

2、现将前两个点放入栈中,然后判断下一个点在这两个点组成的线段的左边还是右边,左边的话,直接加入栈中, 如果在右边的话,就不行了,为了让这个点行,所以栈顶元素出栈,然后在判断栈中前两个组成的线段 跟 这个点个关系...其实这个关键就是不顾一切的让这个点进栈,即使把栈中的元素全部弹出来(当然不会,会留有一个)

3、弄完之后其实最大的那个点已经在栈中了,然后在反过来,从这个最大的开始像之前一样判断。

4、最后弄完,栈顶和栈底都是最小的那个元素。

---------------------------------------------------

三角区域判断:

借助向量,对于OA 和 OB ,如果 Xa Yb - XbYa > 0,OB在OA的右侧,如果小于0,OB在OA的左侧,如果相等共线

---------------------------------------------------------

HD1392

题意:N个点,然后输入N个点的坐标,问形成凸包的周长

 1 #include <iostream>
 2 #include <cstdio>
 3 #include <algorithm>
 4 #include <cmath>
 5 using namespace std;
 6 struct Node
 7 {
 8     int x, y;
 9 };
10 Node node[110], ch[110];
11 int cmp(Node tempx, Node tempy)
12 {
13     if(tempx.y == tempy.y)
14         return tempx.x < tempy.x;
15     return tempx.y < tempy.y;
16 }
17 int xmult(Node p1, Node p2, Node p3)
18 {
19     return (p2.x - p1.x) * (p3.y - p1.y) - (p3.x - p1.x) * (p2.y - p1.y);
20 }
21 double dist(Node p1, Node p2)
22 {
23     return sqrt( (p1.x - p2.x) * (p1.x - p2.x) + (p1.y - p2.y) * (p1.y - p2.y) );
24 }
25 int andrew(int n)
26 {
27     int len, top = 1;
28     ch[0] = node[0];
29     ch[1] = node[1];
30     for(int i = 2; i < n; i++)
31     {
32         while(top && xmult(ch[top - 1], ch[top], node[i]) <= 0) // 保证top>0的情况下才能出栈,因为top等于0,出栈就空了
33             top--;
34         ch[ ++top ] = node[i];
35     }
36     len = top;
37     ch[++top] = node[n - 2];
38     for(int i = n - 3; i >= 0; i--)
39     {
40         while(top != len && xmult(ch[top - 1], ch[top], node[i]) <= 0)  // 这个也要保证当前栈最小是len,如果 > len可以出栈
41             top--;
42         ch[ ++top ] = node[i];
43     }
44     return top;
45 }
46 int main()
47 {
48     int n;
49     while (scanf("%d", &n) != EOF && n)
50     {
51         for(int i = 0; i < n; i++)
52             scanf("%d%d", &node[i].x, &node[i].y);
53         sort(node, node + n, cmp);
54         int top = andrew(n);
55         double ans = 0;
56         //for(int i = 0; i <= top; i++)
57         //    cout << ch[i].x << " " << ch[i].y << endl;
58         for (int i = 1 ; i < top ; i ++)
59           ans += dist(ch[i - 1] , ch[i]);
60         if (top > 2)  // 如果两个点以上还要计算一下栈底 和 次栈底的距离
61             ans += dist(ch[0], ch[top - 1]);
62         printf("%.2lf\n" , ans);
63     }
64     return 0;
65 }
View Code

 

 

posted @ 2016-03-18 14:53  zhaop  阅读(179)  评论(0编辑  收藏  举报