凸包算法

包含点s集合中所有点的最小凸多边形的名字叫凸包

 

Graham扫描算法:

1.从y轴最低点作为起始点p0

2.从p0开始极坐标扫描,依次遍历图中所有的点,按极坐标角度大小,逆时针方向遍历

3.如果新遍历的点能产生一个左旋转,则将该点添加到凸包中,否则舍去

 

实现流程

1.彩色图像转灰度图像

2.灰度图像转二值图像

3.通过发现轮廓得到候选点

4.计算凸包

5.绘制结果 

 

cv::convexHull()

InputArrays Poins 输入候选点

OutputArray hull 凸包集合

bool clockwise 顺时针方向

bool returnPoints 表示返回点个数,如果第二个参数(凸包)是vector<Points>则自动忽略

 

#include<iostream>
#include<vector>
#include<opencv2/opencv.hpp>

using namespace std;
using namespace cv;


int Threshold_value = 100;
int Threshold_max = 255;
Mat src, dst, canny_output, grayImg;
void demo(int, void*);

int main(int argc, char** argv)
{
    
    src = imread("C:/Users/Administrator/Desktop/3.png");
    imshow("input_pic", src);
    cvtColor(src, grayImg, COLOR_BGR2GRAY);
    blur(grayImg, grayImg, Size(3, 3), Point(-1, -1), BORDER_DEFAULT);//标准化盒式过滤器平滑图像
    createTrackbar("Threshold:", "input_pic", &Threshold_value, Threshold_max,demo);
    demo(0, 0);

    waitKey(0);
    return 0;
}

void demo(int, void*)
{
    vector<vector<Point>> points;
    vector<Vec4i>hierachy;
    threshold(grayImg, canny_output, Threshold_value, Threshold_max, THRESH_BINARY);//二值化

    findContours(canny_output, points, hierachy, RETR_TREE, CHAIN_APPROX_SIMPLE, Point(0, 0));

    vector<vector<Point>> convex(points.size());
    for (size_t i = 0; i < points.size(); ++i)
    {
        convexHull(points[i], convex[i], false, true);//凸包算法
    }

    dst = Mat::zeros(grayImg.size(), CV_8UC3);
    vector<Vec4i> empty(0);
    for (size_t i = 0; i < points.size(); ++i)
    {
        Scalar color = Scalar(0,0,255);
        drawContours(dst, points, i, color, 1,LINE_8, empty, 0, Point(0, 0));
    }
    imshow("rslt", dst);
}

 

posted @ 2020-07-21 17:22  Wangtn  阅读(946)  评论(0编辑  收藏  举报