本文废弃,算法更新于:如何判断轮廓是否为圆(算法更新)



    判断一个轮廓是否为圆?这看似简单的问题,在opencv中并没有现成的函数。当我真正想运用的时候,却发现还是有许多内容在里面的。


      

python opencv如何判断一个轮廓的倾斜角度_i++



       比如这幅图片,由于瓶口是有缺陷的,造成找到的最大外轮廓不闭合。那么该如何判断这个轮廓是否是圆了。



     我认为从两点来考虑。



      一个是圆的定义:



   “平面上到定点的距离等于定长的所有点组成的图形叫做圆.定点称为圆心,定长称为半径.”



      那么就来判断当前轮廓到一个定点的距离是否为定长。这里这个定点就可以采用外接圆圆心。而这里的度量是标准差。



       经过试验发现,对于这些有缺陷的情况,其标准差都是比较大的(一般大于5),而对于没有缺陷的情况来说,其标准差都比较小(小于1)。



       但是这并不能完全地解决问题,比如存在这样的情况,其轮廓上所有点到定点的标准差也是不大的,但是这个轮廓没有构成一个闭合曲线,所以也没有构成圆。



python opencv如何判断一个轮廓的倾斜角度_标准差_02



     


   //根据轮廓点和圆心计算方差float ComputeVariance(std::vector<cv::Point> theContour,Point2f theCenter){    int a[65535],n;    float aver,s;    float sum=0,e=0;    n = theContour.size();    for(int i=0;i<n;i++)    {        a[i] = GetDistance(theContour[i],theCenter);        sum+=a[i];    }    aver=sum/n;    for(int i=0;i<n;i++)        e+=(a[i]-aver)*(a[i]-aver);    e/=n-1;    s=sqrt(e);    return e;}


 



        那么二点就是曲线闭合的定义.



      闭曲线:起点与终点重合的曲线。平面(或空间)中的闭曲线即为单位圆周到平面(或空间)中的连续映射的像。



      不是很好理解,但是可以这样简化,就是对于闭曲线中的任意一点,遍历闭曲线,都能够回到这一点。换句话说,就是不存在“端点”。这里可以再转换为这样的理解:



        “对于闭曲线中的所有点,除了它本身之外,和这个点距离为最小值(比如1)的点都有两个。”

//判断轮廓是否闭合。闭合曲线返回为0intComputeClose(std::vector<cv::Point>MaxContour){//TODO 计算第一个点和最后一个点相对于圆心的角度.最后变成计算这两点的距离int itmp =0;int iret =0;for(int i=0;i<MaxContour.size();i++){for(int j=0;j<MaxContour.size();j++){if(i!=j){if(GetDistance(MaxContour[i],MaxContour[j])<1){ itmp++;}}}if(itmp ==1)//存在端点{ iret ++;} itmp=0;}return iret;}


      小结一下:数学还是很强的,很多时候,借助定义本身,能够解决问题。