Hough Transform 霍夫变换检测直线

21 篇文章 0 订阅
14 篇文章 0 订阅

Hough Transform 霍夫变换检测直线

从理论到代码,再从代码到理论

(1)理论之通俗理解:

1.在图像中检测直线的问题,其实质是找到构成直线的所有的像素点。那么问题就是从找到直线,变成找到符合y=mx+c的所有(x,y)的点的问题。

2.进行坐标系变化y=mx+c,变成c=-xm+b。直线上的点(x1,y1),在转换坐标系后为一条直线。这个原理应该是高中的。

  

3.直线上每一个点在MC坐标系中都表现为直线,而且,这些直线都相交于一个点,(m,c)。找到所有点的问题,转变为寻找直线的问题。

4.对于图像中的每一个点,在MC坐标系中对应着很多的直线。找到直线的交点,就对应着找到图像中的直线。

实际在使用这一原理的时候,不是采用直线的斜率和截距公式,而是用

如何实现:

1.       将θ角在-90度到90度的范围里,划分为很多区间,对所有的像素点(x,y)在所有θ角的时候,求出ρ.从而累加ρ值出现的次数。高于某个阈值的ρ就是一个直线。

2.       这个过程就类似于如下一个二维的表格,横坐标就是θ角,ρ就是到直线的最短距离,其实思想就是,为每一个角度的若干个截距都维持一个计数器,然后统计图像上的所有像素点,哪个截距累计的数大就,认为该(斜率,截距)对应一条直线。

横坐标θ不断变换,对于所有的不为0的像素点,计算出ρ,找到ρ在坐标(θ,ρ)的位置累加1.

3.       上图中局部最大的就是找到的直线的θ和ρ的值。

(2) 具体代码片段

 

复制代码
     for( ang =  0, n =  0; n < numangle; ang += theta, n++ )
    {
        tabSin[n] = ( float)(sin(ang) * irho);
        tabCos[n] = ( float)(cos(ang) * irho);
    }

     //  stage 1. fill accumulator
     for( i =  0; i < height; i++ )
         for( j =  0; j < width; j++ )
        {
             if( image[i * step + j] !=  0 )
                 for( n =  0; n < numangle; n++ )
                {
                    r = cvRound( j * tabCos[n] + i * tabSin[n] );
                    r += (numrho -  1) /  2;
                    accum[(n+ 1) * (numrho+ 2) + r+ 1]++;
                }
        }

     //  stage 2. find local maximums
     for( r =  0; r < numrho; r++ )
         for( n =  0; n < numangle; n++ )
        {
             int  base = (n+ 1) * (numrho+ 2) + r+ 1;
             if( accum[ base] > threshold &&
                accum[ base] > accum[ base -  1] && accum[ base] >= accum[ base +  1] &&
                accum[ base] > accum[ base - numrho -  2] && accum[ base] >= accum[ base + numrho +  2] )
                sort_buf[total++] =  base;
        }

     //  stage 3. sort the detected lines by accumulator value
    icvHoughSortDescent32s( sort_buf, total, accum );

     //  stage 4. store the first min(total,linesMax) lines to the output buffer
    linesMax = MIN(linesMax, total);
    scale =  1./(numrho+ 2);
     for( i =  0; i < linesMax; i++ )
    {
        CvLinePolar line;
         int idx = sort_buf[i];
         int n = cvFloor(idx*scale) -  1;
         int r = idx - (n+ 1)*(numrho+ 2) -  1;
        line.rho = (r - (numrho -  1)* 0.5f) * rho;
        line.angle = n * theta;
        cvSeqPush( lines, &line );
    }
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
在MATLAB中,可以使用基于Hough变换直线检测器来检测图像中的直线。该方法利用了Hough变换的原理,通过将图像中的每个像素点转换为霍夫空间中的一条曲线,然后通过对曲线进行计数来确定图像中可能存在的直线。 具体实现可以使用MATLAB中的Hough Transform函数来完成。该函数将图像作为输入,并返回一个Hough累加器矩阵,其中包含了图像中可能的直线“选票”数。 在MATLAB中,可以使用以下代码来实现基于Hough变换直线检测: ``` % 读取图像 image = imread('image.jpg'); % 将图像转换为灰度图像 grayImage = rgb2gray(image); % 对图像应用Canny边缘检测算法 edgeImage = edge(grayImage, 'Canny'); % 应用Hough变换并获取Hough累加器矩阵 [H, theta, rho = hough(edgeImage); % 设置阈值来确定直线 peaks = houghpeaks(H, 10); % 这里的10是阈值参数 % 从Hough累加器矩阵中提取直线段的起始点和结束点 lines = houghlines(edgeImage, theta, rho, peaks); % 显示原始图像和检测到的直线 imshow(image); hold on; for k = 1:length(lines) xy = [lines(k).point1; lines(k).point2]; plot(xy(:,1), xy(:,2), 'LineWidth', 2, 'Color', 'r'); end hold off; ``` 上述代码首先将图像转换为灰度图像,然后应用Canny边缘检测算法来获取图像的边缘信息。接下来,使用Hough Transform函数计算Hough累加器矩阵。然后,使用houghpeaks函数设置阈值来确定直线,并使用houghlines函数从累加器矩阵中提取直线段的起始点和结束点。最后,使用plot函数将检测到的直线显示在原始图像上。 请注意,上述代码仅为示例,具体的参数和阈值需要根据实际情况进行调整。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *2* *3* [基于Hough变换直线检测(Matlab)](https://blog.csdn.net/Yong_Qi2015/article/details/125986218)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 100%"] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值