top of page

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

void cvCanny( const CvArr* image,CvArr* edges,double threshold1,double threshold2, int aperture_size=3 );

 

 

image輸入單通道圖像(可以是彩色圖像)對於多通道的圖像可以用cvCvtColor()修改。

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

edges 輸出的邊緣圖像,也是單通道的,但是是黑白的

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

threshold1第一個閾值

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

threshold2 第二個閾值

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

aperture_size Sobel 算子內核大小

 



小叮嚀:cvCanny只接受單通道圖像作為輸入

 

Canny邊緣檢測算法原理

屬於是先平滑後求導數的方法

Step.1   對原始圖像進行灰度化

Canny算法通常處理的圖像為灰度圖,因此如果攝像機獲取的是彩色圖像,那首先就得進行灰度化。對一幅彩色圖進行灰度化,就是根據圖像各個通道的採樣值進行加權平均。以RGB格式的彩圖為例,通常灰度化採用的方法主要有:

        方法1:Gray=(R+G+B)/3;

        方法2:Gray=0.299R+0.587G+0.114B;(這種參數考慮到了人眼的生理特點)

        注意1:至於其他格式的彩色圖像,可以根據相應的轉換關係轉為RGB然後再進行灰度化;

        注意2:在編程時要注意圖像格式中R->G->B的順序通常為B->G->R。

Step.2     對圖像進行高斯濾波

             圖像高斯濾波的實現可以用兩個一維高斯核分別兩次加權實現,也可以通過一個二維高斯核一次卷積實現。

Step.3    用一階偏導的有限差分來計算梯度的幅值和方向

Canny算法所採用的方法

 

        在本文實現的Canny算法中所採用的捲積算子比較簡單,表達如下:

 

 

 

 

 

 

         

        其x向、y向的一階偏導數矩陣,梯度幅值以及梯度方向的數學表達式為:

 

 

 

 

 

 

 

 

 

 

 

 

 

 

        求出這幾個矩陣後,就可以進行下一步的檢測過程。

 

Step.4        對梯度幅值進行非極大值抑制        

圖像梯度幅值矩陣中的元素值越大,說明圖像中該點的梯度值越大,但這不不能說明該點就是邊緣(這僅僅是屬於圖像增強的過程)。在Canny算法中,非極大值抑制是進行邊緣檢測的重要步驟,通俗意義上是指尋找像素點局部最大值,將非極大值點所對應的灰度值置為0,這樣可以剔除掉一大部分非邊緣的點(這是本人的理解)。

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

根據圖1 可知,要進行非極大值抑制,就首先要確定像素點C的灰度值在其8值鄰域內是否為最大。

圖1中藍色的線條方向為C點的梯度方向,這樣就可以確定其局部的最大值肯定分佈在這條線上,

也即出了C點外,梯度方向的交點dTmp1和dTmp2這兩個點的值也可能會是局部最大值。

因此,判斷C點灰度與這兩個點灰度大小即可判斷C點是否為其鄰域內的局部最大灰度點。

如果經過判斷,C點灰度值小於這兩個點中的任一個,那就說明C點不是局部極大值,那麼則可以排除C點為邊緣。

這就是非極大值抑制的工作原理。

 

作者認為,在理解的過程中需要注意以下兩點:

        (1)中非最大抑制是回答這樣一個問題:"當前的梯度值在梯度方向上是一個局部最大值嗎?"

             所以,要把當前位置的梯度值與梯度方向上兩側的梯度值進行比較;

        (2)梯度方向垂直於邊緣方向。

        但實際上,我們只能得到C點鄰域的8個點的值,而dTmp1和dTmp2並不在其中,

        要得到這兩個值就需要對該兩個點兩端的已知灰度進行線性插值,也即根據圖1中的g1和g2對dTmp1進行插值,

        根據g3和g4對dTmp2進行插值,這要用到其梯度方向,這是上文Canny算法中要求解梯度方向矩陣Thita的原因。

 

        完成非極大值抑制後,會得到一個二值圖像,非邊緣的點灰度值均為0,可能為邊緣的局部灰度極大值點可設置其灰度為128。         根據下文的具體測試圖像可以看出,這樣一個檢測結果還是包含了很多由噪聲及其他原因造成的假邊緣。

        因此還需要進一步的處理。

 

Step.5    用雙閾值算法檢測和連接邊緣

        Canny算法中減少假邊緣數量的方法是採用雙閾值法。

        選擇兩個閾值(關於閾值的選取方法在擴展中進行討論),根據高閾值得到一個邊緣圖像,

        這樣一個圖像含有很少的假邊緣,但是由於閾值較高,產生的圖像邊緣可能不閉合,

        未解決這樣一個問題採用了另外一個低閾值。

 

        在高閾值圖像中把邊緣鏈接成輪廓,當到達輪廓的端點時,該算法會在斷點的8鄰域點中尋找滿足低閾值的點,

        再根據此點收集新的邊緣,直到整個圖像邊緣閉合。

ADDRESS

桃園銘傳大學

Tel: 123-456-7890

TEL HOURS

Mon-Fri: 7am-10pm

Saturday: 8am-10pm

Sunday: 8am-11pm

FACEBOOK ME:

周冠宇
  • Facebook Metallic
  • Twitter Metallic
  • Google Metallic

© 2023 by GROOMSMAN Proudly created with Wix.com

bottom of page