Introduction to SIFT (Scale-Invariant Feature Transform) html
前面講的Harris角點檢測器中的角點在旋轉的圖像中也是角點,可是縮放呢? 若是縮放圖像,則角可能不是角.例如,檢查下面的簡單圖像, 當在同一窗口中放大時,小窗口內的小圖像中的角是平坦的.因此Harris角點檢測器不是尺度不變的.python
因此,在2004年,不列顛哥倫比亞大學的D.Lowe在他的論文中提出了一種新的算法,即尺度不變特徵變換(SIFT).算法
SIFT特徵是基於物體上的一些局部外觀的興趣點而與影像的大小和旋轉無關。對於光線、噪聲、微視角改變的容忍度也至關高.基於這些特性,它們是高度顯著並且相對容易擷取,在母數龐大的特徵數據庫中,很容易辨識物體並且鮮有誤認.使用SIFT特徵描述對於部分物體遮蔽的偵測率也至關高,甚至只須要3個以上的SIFT物體特徵就足以計算出位置與方位.在現今的電腦硬件速度下和小型的特徵數據庫條件下,辨識速度可接近即時運算.SIFT特徵的信息量大,適合在海量數據庫中快速準確匹配.數據庫
import numpy as np import cv2 img = cv2.imread('img.jpg') gray= cv2.cvtColor(img,cv2.COLOR_BGR2GRAY) sift = cv2.xfeatures2d.SIFT_create() kp = sift.detect(gray,None) img=cv2.drawKeypoints(gray,kp,img) cv2.imshow('img',img) cv2.waitKey()
NOTE:
lz直接運行上述代碼時,程序報錯:module 'cv2.cv2' has no attribute 'xfeatures2d'
,後面查詢緣由知道OpenCv3.x之後只包含部份內容,須要神經網絡或者其餘的函數須要導入opencv_contrib,因此須要pip install opencv-contrib-python
數組
sift.detect()
函數在圖像中查找關鍵點, 若是隻想搜索圖像的一部分,能夠傳遞掩膜.
OpenCV還提供了cv2.drawKeyPoints()
函數,該函數在關鍵點的位置上繪製小圓圈.若是傳遞標誌cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS
,它將繪製一個大小爲keypoint的圓圈並顯示它的方向.網絡
import numpy as np import cv2 img = cv2.imread('img.jpg') gray= cv2.cvtColor(img,cv2.COLOR_BGR2GRAY) sift = cv2.xfeatures2d.SIFT_create() kp = sift.detect(gray,None) img=cv2.drawKeypoints(gray,kp,img,flags=cv2.DRAW_MATCHES_FLAGS_DRAW_RICH_KEYPOINTS) cv2.imshow('img',img) cv2.waitKey()
計算描述符,OpenCV提供了兩種方法:函數
sift.compute()
來計算找到的關鍵點的描述符, 例如:kp,des = sift.compute(gary,kp)
sift.detectAndCompute()
在一個步驟中直接查找關鍵點和描述符sift = cv2.xfeatures2d.SIFT_create() kp, des = sift.detectAndCompute(gray,None)
kp是關鍵點列表,des是形狀爲Number_of_Keypoints×128的numpy數組.spa