graham扫描法求凸包集。求任意多边形面积

惯例贴详解
graham扫描法这个图片不错 https://blog.csdn.net/neau2014/article/details/48225965
然后就是代码如何实现 https://www.cnblogs.com/wpbing/p/9456240.html

struct Point{
    double x, y;
}p[1100], st[1100];

叉积(叉乘):
double X(double x1, double y1, double x2, double y2){ 
    return x1*y2 - y1*x2;
}

线段长:
double dis(Point a, Point b){
    double sum1 = abs(b.x-a.x);
    double sum2 = abs(b.y-a.y);
    return sqrt(sum1*sum1 + sum2*sum2);
}

极角排序:
bool cmp(Point a, Point b){ 
    double x = X(a.x - p[1].x, a.y-p[1].y, b.x - p[1].x, b.y-p[1].y);
    if(x > 0) return 1;
    if(!x && dis(a, p[1]) > dis(b, p[1])) return 1;
    return 0;
}

判断ac是否在ab的顺时针方向,凸包上的连续三个点a.b.c应该ac在ab顺时针方向:
bool judge(Point a, Point b, Point c){ 
    if(X(b.x-a.x, b.y-a.y, c.x-a.x, c.y-a.y) > 0) return 1;
    return 0; 
}

求凸包集合s:
void solve(){ 
    s[1] = p[1];
    s[2] = p[2]; //前两个点初始点
    int pos = 2; //表示凸包集合栈顶
    for(int i = 3; i <= n; i++){
        while(t > 2 && !judge(s[pos-1], s[pos], p[i])) pos--;
        s[++pos] = p[i];
    }
}
求凸包周长:
double L(){ 
    double sum = 0;
    for(int i=1;i<t;i++){
        sum+=dis(s[i],s[i+1]);
    }
}

求任意多边形面积(点集已经按照顺时针或者逆时针排好序了):
提示: s = (ab*sin0)/2 即a向量和b向量叉乘的一半

double S(){ 
    if(n < 3) return 0;
    double sum = 0;
    p[n + 1] = p[1]; //画个图就知道了
    for(int i = 1; i <= n; i++)
        sum += p[i].x * p[i + 1].y - p[i].y * p[i + 1].x;
        //可以理解为不管这个多边形在哪,都以原点为分割点,
        //就算原点在外面也可以算出,因为有正负可以抵消掉多余的
    return fabs(sum / 2.0);
}

有段话我左看右看就不知道哪里触动赵家人了,相册都给我屏蔽:
清华郭于华:我未必能唤醒周围的人,我只是挣扎着不让自己沉睡;我没能力推翻一堵墙,但我不会给这堵墙增加哪怕一块砖;我注定改变不了权势,我只是抗争着不让权势改变我;我可能一辈子看不到未来,但我永远铭记着自己的信仰和方向。每个人灵魂深处都有颗种子,有人选择弃置,有人会给他创造成长的土壤。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值