首頁人工智能技術(shù)資訊正文

SIFT算法原理:SIFT算法詳細介紹

更新時間:2021-06-04 來源:黑馬程序員 瀏覽量:

前面我們介紹了Harris和Shi-Tomasi角點檢測算法,這兩種算法具有旋轉(zhuǎn)不變性,但不具有尺度不變性,以下圖為例,在左側(cè)小圖中可以檢測到角點,但是圖像被放大后,在使用同樣的窗口,就檢測不到角點了。

SIFT算法01

所以,下面我們來介紹一種計算機視覺的算法,尺度不變特征轉(zhuǎn)換即SIFT (Scale-invariant feature transform)。它用來偵測與描述影像中的局部性特征,它在空間尺度中尋找極值點,并提取出其位置、尺度、旋轉(zhuǎn)不變量,此算法由 David Lowe在1999年所發(fā)表,2004年完善總結(jié)。應(yīng)用范圍包含物體辨識、機器人地圖感知與導(dǎo)航、影像縫合、3D模型建立、手勢辨識、影像追蹤和動作比對等領(lǐng)域。

SIFT算法的實質(zhì)是在不同的尺度空間上查找關(guān)鍵點(特征點),并計算出關(guān)鍵點的方向。SIFT所查找到的關(guān)鍵點是一些十分突出,不會因光照,仿射變換和噪音等因素而變化的點,如角點、邊緣點、暗區(qū)的亮點及亮區(qū)的暗點等。

1.1 基本流程

Lowe將SIFT算法分解為如下四步

尺度空間極值檢測:搜索所有尺度上的圖像位置。通過高斯差分函數(shù)來識別潛在的對于尺度和旋轉(zhuǎn)不變的關(guān)鍵點。

關(guān)鍵點定位:在每個候選的位置上,通過一個擬合精細的模型來確定位置和尺度。關(guān)鍵點的選擇依據(jù)于它們的穩(wěn)定程度。

關(guān)鍵點方向確定:基于圖像局部的梯度方向,分配給每個關(guān)鍵點位置一個或多個方向。所有后面的對圖像數(shù)據(jù)的操作都相對于關(guān)鍵點的方向、尺度和位置進行變換,從而保證了對于這些變換的不變性。

關(guān)鍵點描述:在每個關(guān)鍵點周圍的鄰域內(nèi),在選定的尺度上測量圖像局部的梯度。這些梯度作為關(guān)鍵點的描述符,它允許比較大的局部形狀的變形或光照變化。

我們就沿著Lowe的步驟,對SIFT算法的實現(xiàn)過程進行介紹:

1.2 尺度空間極值檢測

在不同的尺度空間是不能使用相同的窗口檢測極值點,對小的關(guān)鍵點使用小的窗口,對大的關(guān)鍵點使用大的窗口,為了達到上述目的,我們使用尺度空間濾波器。

高斯核是唯一可以產(chǎn)生多尺度空間的核函數(shù)。-《Scale-space theory: A basic tool for analysing structures at different scales》。

一個圖像的尺度空間L(x,y,σ),定義為原始圖像I(x,y)與一個可變尺度的2維高斯函數(shù)G(x,y,σ)卷積運算 ,即:

L ( x , y , σ ) = G ( x , y , σ ) ? I ( x , y ) L(x,y,\sigma) = G(x,y,\sigma)* I(x,y) 其中: G ( x , y , σ ) = 1 2 π σ 2 e ? x 2 + y 2 2 σ 2 G(x,y,\sigma)=\frac{1}{2\pi\sigma^2}e^{-\frac{x^2+y^2}{2\sigma^2}} σ \sigma 是尺度空間因子,它決定了圖像的模糊的程度。在大尺度下( σ \sigma 值大)表現(xiàn)的是圖像的概貌信息,在小尺度下( σ \sigma 值?。┍憩F(xiàn)的是圖像的細節(jié)信息。

在計算高斯函數(shù)的離散近似時,在大概3σ距離之外的像素都可以看作不起作用,這些像素的計算也就可以忽略。所以,在實際應(yīng)用中,只計算(6σ+1)*(6σ+1)的高斯卷積核就可以保證相關(guān)像素影響。

下面我們構(gòu)建圖像的高斯金字塔,它采用高斯函數(shù)對圖像進行模糊以及降采樣處理得到的,高斯金字塔構(gòu)建過程中,首先將圖像擴大一倍,在擴大的圖像的基礎(chǔ)之上構(gòu)建高斯金字塔,然后對該尺寸下圖像進行高斯模糊,幾幅模糊之后的圖像集合構(gòu)成了一個Octave,然后對該Octave下選擇一幅圖像進行下采樣,長和寬分別縮短一倍,圖像面積變?yōu)樵瓉硭姆种弧_@幅圖像就是下一個Octave的初始圖像,在初始圖像的基礎(chǔ)上完成屬于這個Octave的高斯模糊處理,以此類推完成整個算法所需要的所有八度構(gòu)建,這樣這個高斯金字塔就構(gòu)建出來了,整個流程如下圖所示:

SIFT原理02

利用LoG(高斯拉普拉斯方法),即圖像的二階導(dǎo)數(shù),可以在不同的尺度下檢測圖像的關(guān)鍵點信息,從而確定圖像的特征點。但LoG的計算量大,效率低。所以我們通過兩個相鄰高斯尺度空間的圖像的相減,得到DoG(高斯差分)來近似LoG。

為了計算DoG我們構(gòu)建高斯差分金字塔,該金字塔是在上述的高斯金字塔的基礎(chǔ)上構(gòu)建而成的,建立過程是:在高斯金字塔中每個Octave中相鄰兩層相減就構(gòu)成了高斯差分金字塔。如下圖所示:

SIFT算法03

高斯差分金字塔的第1組第1層是由高斯金字塔的第1組第2層減第1組第1層得到的。以此類推,逐組逐層生成每一個差分圖像,所有差分圖像構(gòu)成差分金字塔。概括為DOG金字塔的第o組第l層圖像是有高斯金字塔的第o組第l+1層減第o組第l層得到的。后續(xù)Sift特征點的提取都是在DOG金字塔上進行的

在 DoG 搞定之后,就可以在不同的尺度空間中搜索局部最大值了。對于圖像中的一個像素點而言,它需要與自己周圍的 8 鄰域,以及尺度空間中上下兩層中的相鄰的 18(2x9)個點相比。如果是局部最大值,它就可能是一個關(guān)鍵點?;旧蟻碚f關(guān)鍵點是圖像在相應(yīng)尺度空間中的最好代表。如下圖所示:

SIFT算法03

搜索過程從每組的第二層開始,以第二層為當(dāng)前層,對第二層的DoG圖像中的每個點取一個3×3的立方體,立方體上下層為第一層與第三層。這樣,搜索得到的極值點既有位置坐標(biāo)(DoG的圖像坐標(biāo)),又有空間尺度坐標(biāo)(層坐標(biāo))。當(dāng)?shù)诙铀阉魍瓿珊?,再以第三層作為?dāng)前層,其過程與第二層的搜索類似。當(dāng)S=3時,每組里面要搜索3層,所以在DOG中就有S+2層,在初使構(gòu)建的金字塔中每組有S+3層。

1.3 關(guān)鍵點定位

由于DoG對噪聲和邊緣比較敏感,因此在上面高斯差分金字塔中檢測到的局部極值點需經(jīng)過進一步的檢驗才能精確定位為特征點。

使用尺度空間的泰勒級數(shù)展開來獲得極值的準(zhǔn)確位置, 如果極值點的 灰度值小于閾值(一般為0.03或0.04)就會被忽略掉。 在 OpenCV 中這種閾值被稱為 contrastThreshold。

DoG 算法對邊界非常敏感, 所以我們必須要把邊界去除。 Harris 算法除了可以用于角點檢測之外還可以用于檢測邊界。從 Harris 角點檢測的算法中,當(dāng)一個特征值遠遠大于另外一個特征值時檢測到的是邊界。那在DoG算法中欠佳的關(guān)鍵點在平行邊緣的方向有較大的主曲率,而在垂直于邊緣的方向有較小的曲率,兩者的比值如果高于某個閾值(在OpenCV中叫做邊界閾值),就認(rèn)為該關(guān)鍵點為邊界,將被忽略,一般將該閾值設(shè)置為10。

將低對比度和邊界的關(guān)鍵點去除,得到的就是我們感興趣的關(guān)鍵點。

1.4 關(guān)鍵點方向確定

經(jīng)過上述兩個步驟,圖像的關(guān)鍵點就完全找到了,這些關(guān)鍵點具有尺度不變性。為了實現(xiàn)旋轉(zhuǎn)不變性,還需要為每個關(guān)鍵點分配一個方向角度,也就是根據(jù)檢測到的關(guān)鍵點所在高斯尺度圖像的鄰域結(jié)構(gòu)中求得一個方向基準(zhǔn)。

對于任一關(guān)鍵點,我們采集其所在高斯金字塔圖像以r為半徑的區(qū)域內(nèi)所有像素的梯度特征(幅值和幅角),半徑r為: r = 3 × 1 . 5 σ r = 3\times1.5\sigma 其中σ是關(guān)鍵點所在octave的圖像的尺度,可以得到對應(yīng)的尺度圖像。

梯度的幅值和方向的計算公式為: m ( x , y ) = ( L ( x + 1 , y ) ? L ( x ? 1 , y ) 2 + ( L ( x , y + 1 ) ? L ( x , y ? 1 ) ) 2 m(x,y)=\sqrt{(L(x+1,y)-L(x-1,y)^2+(L(x,y+1)-L(x,y-1))^2}

θ ( x , y ) = a r c t a n ( L ( x , y + 1 ) ? L ( x , y ? 1 ) L ( x + 1 , y ) ? L ( x ? 1 ) , y ) \theta(x,y) = arctan(\frac{L(x,y+1)-L(x,y-1)}{L(x+1,y)-L(x-1),y})

鄰域像素梯度的計算結(jié)果如下圖所示:

SIFT算法05

完成關(guān)鍵點梯度計算后,使用直方圖統(tǒng)計關(guān)鍵點鄰域內(nèi)像素的梯度幅值和方向。具體做法是,將360°分為36柱,每10°為一柱,然后在以r為半徑的區(qū)域內(nèi),將梯度方向在某一個柱內(nèi)的像素找出來,然后將他們的幅值相加在一起作為柱的高度。因為在r為半徑的區(qū)域內(nèi)像素的梯度幅值對中心像素的貢獻是不同的,因此還需要對幅值進行加權(quán)處理,采用高斯加權(quán),方差為1.5σ。如下圖所示,為簡化圖中只畫了8個方向的直方圖。

SIFT算法06

每個特征點必須分配一個主方向,還需要一個或多個輔方向,增加輔方向的目的是為了增強圖像匹配的魯棒性。輔方向的定義是,當(dāng)一個柱體的高度大于主方向柱體高度的80%時,則該柱體所代表的的方向就是給特征點的輔方向。

直方圖的峰值,即最高的柱代表的方向是特征點鄰域范圍內(nèi)圖像梯度的主方向,但該柱體代表的角度是一個范圍,所以我們還要對離散的直方圖進行插值擬合,以得到更精確的方向角度值。利用拋物線對離散的直方圖進行擬合,如下圖所示:

SIFT算法07

獲得圖像關(guān)鍵點主方向后,每個關(guān)鍵點有三個信息(x,y,σ,θ):位置、尺度、方向。由此我們可以確定一個SIFT特征區(qū)域。通常使用一個帶箭頭的圓或直接使用箭頭表示SIFT區(qū)域的三個值:中心表示特征點位置,半徑表示關(guān)鍵點尺度,箭頭表示方向。如下圖所示:

SIFT算法08

1.5 關(guān)鍵點描述

通過以上步驟,每個關(guān)鍵點就被分配了位置,尺度和方向信息。接下來我們?yōu)槊總€關(guān)鍵點建立一個描述符,該描述符既具有可區(qū)分性,又具有對某些變量的不變性,如光照,視角等。而且描述符不僅僅包含關(guān)鍵點,也包括關(guān)鍵點周圍對其有貢獻的的像素點。主要思路就是通過將關(guān)鍵點周圍圖像區(qū)域分塊,計算塊內(nèi)的梯度直方圖,生成具有特征向量,對圖像信息進行抽象。

描述符與特征點所在的尺度有關(guān),所以我們在關(guān)鍵點所在的高斯尺度圖像上生成對應(yīng)的描述符。以特征點為中心,將其附近鄰域劃分為 d ? d d*d 個子區(qū)域(一般取d=4),每個子區(qū)域都是一個正方形,邊長為3σ,考慮到實際計算時,需進行三次線性插值,所以特征點鄰域的為 3 σ ( d + 1 ) ? 3 σ ( d + 1 ) 3\sigma(d+1)*3\sigma(d+1) 的范圍,如下圖所示:

SIFT算法09

為了保證特征點的旋轉(zhuǎn)不變性,以特征點為中心,將坐標(biāo)軸旋轉(zhuǎn)為關(guān)鍵點的主方向,如下圖所示:

SIFT算法10

計算子區(qū)域內(nèi)的像素的梯度,并按照σ=0.5d進行高斯加權(quán),然后插值計算得到每個種子點的八個方向的梯度,插值方法如下圖所示:

SIFT算法11

每個種子點的梯度都是由覆蓋其的4個子區(qū)域插值而得的。如圖中的紅色點,落在第0行和第1行之間,對這兩行都有貢獻。對第0行第3列種子點的貢獻因子為dr,對第1行第3列的貢獻因子為1-dr,同理,對鄰近兩列的貢獻因子為dc和1-dc,對鄰近兩個方向的貢獻因子為do和1-do。則最終累加在每個方向上的梯度大小為: w e i g h t = w ? d r k ( 1 ? d r ) ( 1 ? k ) d c m ( 1 ? d c ) 1 ? m d o n ( 1 ? d o ) 1 ? n weight = w*dr^k(1-dr)^{(1-k)}dc^m(1-dc)^{1-m}do^n(1-do)^{1-n} 其中k,m,n為0或為1。 如上統(tǒng)計 4 ? 4 ? 8 = 1 2 8 4*4*8=128 個梯度信息即為該關(guān)鍵點的特征向量,按照特征點的對每個關(guān)鍵點的特征向量進行排序,就得到了SIFT特征描述向量。

1.6 總結(jié)

SIFT在圖像的不變特征提取方面擁有無與倫比的優(yōu)勢,但并不完美,仍然存在實時性不高,有時特征點較少,對邊緣光滑的目標(biāo)無法準(zhǔn)確提取特征點等缺陷,自SIFT算法問世以來,人們就一直對其進行優(yōu)化和改進,其中最著名的就是SURF算法。



猜你喜歡:

線性回歸定義和線性回歸方程公式

集成學(xué)習(xí)算法是什么?如何理解集成學(xué)習(xí)?

什么是KNN算法?

深度相機常見技術(shù):深度相機的相位求解

黑馬程序員人工智能培訓(xùn)課程

分享到:
在線咨詢 我要報名
和我們在線交談!