最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

應(yīng)用OpenCV和Python進(jìn)行SIFT算法的實(shí)現(xiàn)詳解

 更新時(shí)間:2019年08月21日 11:19:25   作者:章子雎Kevin  
這篇文章主要介紹了應(yīng)用OpenCV和Python進(jìn)行SIFT算法的實(shí)現(xiàn)詳解,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧

應(yīng)用OpenCV和Python進(jìn)行SIFT算法的實(shí)現(xiàn)

如下圖為進(jìn)行測(cè)試的gakki101和gakki102,分別驗(yàn)證基于BFmatcher、FlannBasedMatcher等的SIFT算法,對(duì)比其優(yōu)劣。為體現(xiàn)出匹配效果對(duì)于旋轉(zhuǎn)特性的優(yōu)勢(shì),將圖gakki101做成具有旋轉(zhuǎn)特性的效果。

這里寫圖片描述

基于BFmatcher的SIFT實(shí)現(xiàn)

BFmatcher(Brute-Force Matching)暴力匹配,應(yīng)用BFMatcher.knnMatch( )函數(shù)來進(jìn)行核心的匹配,knnMatch(k-nearest neighbor classification)k近鄰分類算法。

kNN算法則是從訓(xùn)練集中找到和新數(shù)據(jù)最接近的k條記錄,然后根據(jù)他們的主要分類來決定新數(shù)據(jù)的類別。該算法涉及3個(gè)主要因素:訓(xùn)練集、距離或相似的衡量、k的大小。kNN算法的核心思想是如果一個(gè)樣本在特征空間中的k個(gè)最相鄰的樣本中的大多數(shù)屬于某一個(gè)類別,則該樣本也屬于這個(gè)類別,并具有這個(gè)類別上樣本的特性。該方法在確定分類決策上只依據(jù)最鄰近的一個(gè)或者幾個(gè)樣本的類別來決定待分樣本所屬的類別。

kNN方法在類別決策時(shí),只與極少量的相鄰樣本有關(guān)。由于kNN方法主要靠周圍有限的鄰近的樣本,而不是靠判別類域的方法來確定所屬類別的,因此對(duì)于類域的交叉或重疊較多的待分樣本集來說,kNN方法較其他方法更為適合。
經(jīng)檢驗(yàn) BFmatcher在做匹配時(shí)會(huì)耗費(fèi)大量的時(shí)間。

代碼段如下:

import numpy as np
import cv2
from matplotlib import pyplot as plt

imgname1 = 'E:/other/gakki101.jpg'
imgname2 = 'E:/other/gakki102.jpg'

sift = cv2.xfeatures2d.SIFT_create()

img1 = cv2.imread(imgname1)
gray1 = cv2.cvtColor(img1, cv2.COLOR_BGR2GRAY) #灰度處理圖像
kp1, des1 = sift.detectAndCompute(img1,None)  #des是描述子

img2 = cv2.imread(imgname2)
gray2 = cv2.cvtColor(img2, cv2.COLOR_BGR2GRAY)#灰度處理圖像
kp2, des2 = sift.detectAndCompute(img2,None) #des是描述子

hmerge = np.hstack((gray1, gray2)) #水平拼接
cv2.imshow("gray", hmerge) #拼接顯示為gray
cv2.waitKey(0)

img3 = cv2.drawKeypoints(img1,kp1,img1,color=(255,0,255)) #畫出特征點(diǎn),并顯示為紅色圓圈
img4 = cv2.drawKeypoints(img2,kp2,img2,color=(255,0,255)) #畫出特征點(diǎn),并顯示為紅色圓圈
hmerge = np.hstack((img3, img4)) #水平拼接
cv2.imshow("point", hmerge) #拼接顯示為gray
cv2.waitKey(0)
# BFMatcher解決匹配
bf = cv2.BFMatcher()
matches = bf.knnMatch(des1,des2, k=2)
# 調(diào)整ratio
good = []
for m,n in matches:
  if m.distance < 0.75*n.distance:
    good.append([m])

img5 = cv2.drawMatchesKnn(img1,kp1,img2,kp2,matches,None,flags=2)
cv2.imshow("BFmatch", img5)
cv2.waitKey(0)
cv2.destroyAllWindows()

首先是針對(duì)圖像的灰度化顯示:

這里寫圖片描述

之后完成特征點(diǎn)的標(biāo)注,用紅色圓圈表示:

這里寫圖片描述

在cv2.drawMatchesKnn(img1,kp1,img2,kp2,matches,None,flags=2)下的匹配效果,比較雜亂,且會(huì)出錯(cuò)。

這里寫圖片描述

如果更換為cv2.drawMatchesKnn(img1,kp1,img2,kp2,good,None,flags=2),明顯優(yōu)于上面的匹配,并且為預(yù)想的匹配區(qū)域,其效果為:

這里寫圖片描述

基于FlannBasedMatcher的SIFT實(shí)現(xiàn)

FLANN(Fast_Library_for_Approximate_Nearest_Neighbors)快速最近鄰搜索包,它是一個(gè)對(duì)大數(shù)據(jù)集和高維特征進(jìn)行最近鄰搜索的算法的集合,而且這些算法都已經(jīng)被優(yōu)化過了。在面對(duì)大數(shù)據(jù)集時(shí)它的效果要好于 BFMatcher。
經(jīng)驗(yàn)證,F(xiàn)LANN比其他的最近鄰搜索軟件快10倍。使用 FLANN 匹配,我們需要傳入兩個(gè)字典作為參數(shù)。這兩個(gè)用來確定要使用的算法和其他相關(guān)參數(shù)等。

第一個(gè)是 IndexParams。
index_params = dict(algorithm = FLANN_INDEX_KDTREE, trees = 5) 。
這里使用的是KTreeIndex配置索引,指定待處理核密度樹的數(shù)量(理想的數(shù)量在1-16)。

第二個(gè)字典是SearchParams
search_params = dict(checks=100)用它來指定遞歸遍歷的次數(shù)。值越高結(jié)果越準(zhǔn)確,但是消耗的時(shí)間也越多。實(shí)際上,匹配效果很大程度上取決于輸入。

5kd-trees50checks總能取得合理精度,而且短時(shí)間完成。在之下的代碼中,丟棄任何距離大于0.7的值,則可以避免幾乎90%的錯(cuò)誤匹配,但是好的匹配結(jié)果也會(huì)很少。

import numpy as np
import cv2
from matplotlib import pyplot as plt

imgname1 = 'E:/other/gakki101.jpg'
imgname2 = 'E:/other/gakki102.jpg'

sift = cv2.xfeatures2d.SIFT_create()

# FLANN 參數(shù)設(shè)計(jì)
FLANN_INDEX_KDTREE = 0
index_params = dict(algorithm = FLANN_INDEX_KDTREE, trees = 5)
search_params = dict(checks=50)
flann = cv2.FlannBasedMatcher(index_params,search_params)

img1 = cv2.imread(imgname1)
gray1 = cv2.cvtColor(img1, cv2.COLOR_BGR2GRAY) #灰度處理圖像
kp1, des1 = sift.detectAndCompute(img1,None)#des是描述子

img2 = cv2.imread(imgname2)
gray2 = cv2.cvtColor(img2, cv2.COLOR_BGR2GRAY)
kp2, des2 = sift.detectAndCompute(img2,None)

hmerge = np.hstack((gray1, gray2)) #水平拼接
cv2.imshow("gray", hmerge) #拼接顯示為gray
cv2.waitKey(0)

img3 = cv2.drawKeypoints(img1,kp1,img1,color=(255,0,255))
img4 = cv2.drawKeypoints(img2,kp2,img2,color=(255,0,255))

hmerge = np.hstack((img3, img4)) #水平拼接
cv2.imshow("point", hmerge) #拼接顯示為gray
cv2.waitKey(0)
matches = flann.knnMatch(des1,des2,k=2)
matchesMask = [[0,0] for i in range(len(matches))]

good = []
for m,n in matches:
  if m.distance < 0.7*n.distance:
    good.append([m])

img5 = cv2.drawMatchesKnn(img1,kp1,img2,kp2,matches,None,flags=2)
cv2.imshow("FLANN", img5)
cv2.waitKey(0)
cv2.destroyAllWindows()

首先是針對(duì)圖像的灰度化顯示:

這里寫圖片描述

之后完成特征點(diǎn)的標(biāo)注,用紅色圓圈表示:

這里寫圖片描述

在cv2.drawMatchesKnn(img1,kp1,img2,kp2,matches,None,flags=2)下的匹配效果,比較雜亂,且會(huì)出錯(cuò)。

這里寫圖片描述

如果更換為cv2.drawMatchesKnn(img1,kp1,img2,kp2,good,None,flags=2),明顯優(yōu)于上面的匹配,并且為預(yù)想的匹配區(qū)域,其效果為:

這里寫圖片描述

修改if m.distance < 0.7*n.distance:為 if m.distance < 1*n.distance:,顯示效果為:

這里寫圖片描述

可見,雖然值越大,匹配的線條越密集,但錯(cuò)誤匹配點(diǎn)也會(huì)增多,在lowe論文中,Lowe推薦ratio的閾值為0.8,但作者對(duì)大量任意存在尺度、旋轉(zhuǎn)和亮度變化的兩幅圖片進(jìn)行匹配,結(jié)果表明ratio取值在0. 4~0. 6 之間最佳,小于0. 4的很少有匹配點(diǎn),大于0. 6的則存在大量錯(cuò)誤匹配點(diǎn),所以建議ratio的取值原則如下:

ratio=0. 4:對(duì)于準(zhǔn)確度要求高的匹配;
ratio=0. 6:對(duì)于匹配點(diǎn)數(shù)目要求比較多的匹配;
ratio=0. 5:一般情況下。

基于FlannBasedMatcher的SURF實(shí)現(xiàn)

SURF全稱為“加速穩(wěn)健特征”(Speeded Up Robust Feature),不僅是尺度不變特征,而且是具有較高計(jì)算效率的特征??杀徽J(rèn)為SURF是尺度不變特征變換算法(SIFT算法)的加速版。SURF最大的特征在于采用了haar特征以及積分圖像的概念,SIFT采用的是DoG圖像,而SURF采用的是Hessian矩陣(SURF算法核心)行列式近似值圖像。SURF借鑒了SIFT算法中簡(jiǎn)化近似的思想,實(shí)驗(yàn)證明,SURF算法較SIFT算法在運(yùn)算速度上要快3倍,綜合性優(yōu)于SIFT算法。

import numpy as np
import cv2
from matplotlib import pyplot as plt

imgname1 = 'E:/other/gakki101.jpg'
imgname2 = 'E:/other/gakki102.jpg'

surf = cv2.xfeatures2d.SURF_create()

FLANN_INDEX_KDTREE = 0
index_params = dict(algorithm = FLANN_INDEX_KDTREE, trees = 5)
search_params = dict(checks=50)
flann = cv2.FlannBasedMatcher(index_params,search_params)

img1 = cv2.imread(imgname1)
gray1 = cv2.cvtColor(img1, cv2.COLOR_BGR2GRAY) #灰度處理圖像
kp1, des1 = surf.detectAndCompute(img1,None)#des是描述子

img2 = cv2.imread(imgname2)
gray2 = cv2.cvtColor(img2, cv2.COLOR_BGR2GRAY)
kp2, des2 = surf.detectAndCompute(img2,None)

hmerge = np.hstack((gray1, gray2)) #水平拼接
cv2.imshow("gray", hmerge) #拼接顯示為gray
cv2.waitKey(0)

img3 = cv2.drawKeypoints(img1,kp1,img1,color=(255,0,255))
img4 = cv2.drawKeypoints(img2,kp2,img2,color=(255,0,255))

hmerge = np.hstack((img3, img4)) #水平拼接
cv2.imshow("point", hmerge) #拼接顯示為gray
cv2.waitKey(0)

matches = flann.knnMatch(des1,des2,k=2)

good = []
for m,n in matches:
  if m.distance < 0.7*n.distance:
    good.append([m])
img5 = cv2.drawMatchesKnn(img1,kp1,img2,kp2,good,None,flags=2)
cv2.imshow("SURF", img5)
cv2.waitKey(0)
cv2.destroyAllWindows()

在cv2.drawMatchesKnn(img1,kp1,img2,kp2,matches,None,flags=2)下的匹配效果,比較雜亂,且會(huì)出錯(cuò)。

如果更換為cv2.drawMatchesKnn(img1,kp1,img2,kp2,good,None,flags=2),明顯優(yōu)于上面的匹配,并且為預(yù)想的匹配區(qū)域,其效果為:

這里寫圖片描述

但就其錯(cuò)誤點(diǎn)數(shù)量和匹配效果而言,并沒有SIFT來的理想。

基于BFMatcher的ORB實(shí)現(xiàn)

ORB(Oriented Fast and Rotated BRIEF),結(jié)合Fast與Brief算法,并給Fast特征點(diǎn)增加了方向性,使得特征點(diǎn)具有旋轉(zhuǎn)不變性,并提出了構(gòu)造金字塔方法,解決尺度不變性,但文章中沒有具體詳述。特征提取是由FAST(Features from Accelerated Segment Test)算法發(fā)展來的,特征點(diǎn)描述是根據(jù)BRIEF(Binary Robust Independent Elementary Features)特征描述算法改進(jìn)的。ORB特征是將FAST特征點(diǎn)的檢測(cè)方法與BRIEF特征描述子結(jié)合起來,并在它們?cè)瓉淼幕A(chǔ)上做了改進(jìn)與優(yōu)化。ORB主要解決BRIEF描述子不具備旋轉(zhuǎn)不變性的問題。實(shí)驗(yàn)證明,ORB遠(yuǎn)優(yōu)于之前的SIFT與SURF算法,ORB算法的速度是sift的100倍,是surf的10倍。

import numpy as np
import cv2
from matplotlib import pyplot as plt

imgname1 = 'E:/other/gakki101.jpg'
imgname2 = 'E:/other/gakki102.jpg'

orb = cv2.ORB_create()

img1 = cv2.imread(imgname1)
gray1 = cv2.cvtColor(img1, cv2.COLOR_BGR2GRAY) #灰度處理圖像
kp1, des1 = orb.detectAndCompute(img1,None)#des是描述子

img2 = cv2.imread(imgname2)
gray2 = cv2.cvtColor(img2, cv2.COLOR_BGR2GRAY)
kp2, des2 = orb.detectAndCompute(img2,None)

hmerge = np.hstack((gray1, gray2)) #水平拼接
cv2.imshow("gray", hmerge) #拼接顯示為gray
cv2.waitKey(0)

img3 = cv2.drawKeypoints(img1,kp1,img1,color=(255,0,255))
img4 = cv2.drawKeypoints(img2,kp2,img2,color=(255,0,255))

hmerge = np.hstack((img3, img4)) #水平拼接
cv2.imshow("point", hmerge) #拼接顯示為gray
cv2.waitKey(0)

# BFMatcher解決匹配
bf = cv2.BFMatcher()
matches = bf.knnMatch(des1,des2, k=2)
# 調(diào)整ratio
good = []
for m,n in matches:
  if m.distance < 0.75*n.distance:
    good.append([m])

img5 = cv2.drawMatchesKnn(img1,kp1,img2,kp2,good,None,flags=2)
cv2.imshow("ORB", img5)
cv2.waitKey(0)
cv2.destroyAllWindows()

經(jīng)顯示觀察到,ORB算法在特征點(diǎn)標(biāo)記時(shí)數(shù)量較少,如圖:

在cv2.drawMatchesKnn(img1,kp1,img2,kp2,matches,None,flags=2)下的匹配效果,比較雜亂,且會(huì)出錯(cuò)。

這里寫圖片描述

如果更換為cv2.drawMatchesKnn(img1,kp1,img2,kp2,good,None,flags=2),明顯優(yōu)于上面的匹配,并且為預(yù)想的匹配區(qū)域,其效果為:

這里寫圖片描述

但同樣會(huì)出現(xiàn)在同樣的匹配方式上,效果不如SIFT的現(xiàn)象。
如下為使用FAST作為特征描述的關(guān)鍵代碼和提取圖像顯示:

import numpy as np
import cv2
from matplotlib import pyplot as plt

img = cv2.imread('E:/other/gakki102.',0)

fast=cv2.FastFeatureDetector_create()#獲取FAST角點(diǎn)探測(cè)器
kp=fast.detect(img,None)#描述符
img = cv2.drawKeypoints(img,kp,img,color=(255,255,0))#畫到img上面
print ("Threshold: ", fast.getThreshold())#輸出閾值
print ("nonmaxSuppression: ", fast.getNonmaxSuppression())#是否使用非極大值抑制
print ("Total Keypoints with nonmaxSuppression: ", len(kp))#特征點(diǎn)個(gè)數(shù)
cv2.imshow('fast',img)
cv2.waitKey(0)

如圖為FAST特征提取的圖像顯示:

這里寫圖片描述

以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。

相關(guān)文章

  • 詳解如何利用Pytest?Cache?Fixture實(shí)現(xiàn)測(cè)試結(jié)果緩存

    詳解如何利用Pytest?Cache?Fixture實(shí)現(xiàn)測(cè)試結(jié)果緩存

    這篇文章主要為大家詳細(xì)介紹了如何利用Pytest?Cache?Fixture實(shí)現(xiàn)測(cè)試結(jié)果緩存,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以跟隨小編一起了解一下
    2023-09-09
  • Python通過文本和圖片生成詞云圖

    Python通過文本和圖片生成詞云圖

    這篇文章主要介紹了Python通過文本和圖片生成詞云圖,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下
    2020-05-05
  • jupyter notebook保存文件默認(rèn)路徑更改方法匯總(親測(cè)可以)

    jupyter notebook保存文件默認(rèn)路徑更改方法匯總(親測(cè)可以)

    安裝Anaconda后,新建文件的默認(rèn)存儲(chǔ)路徑一般在C系統(tǒng)盤,那么路徑是什么呢?如何更改jupyter notebook保存文件默認(rèn)路徑呢?今天小編就這一問題通過兩種方法給大家講解,需要的朋友跟隨小編一起看看吧
    2021-06-06
  • Python寫腳本常用模塊OS基礎(chǔ)用法詳解

    Python寫腳本常用模塊OS基礎(chǔ)用法詳解

    這篇文章主要介紹了Python寫腳本常用模塊OS基礎(chǔ)用法詳解,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-03-03
  • 詳解python中的數(shù)據(jù)類型和控制流

    詳解python中的數(shù)據(jù)類型和控制流

    這篇文章主要介紹了詳解python中的數(shù)據(jù)類型和控制流,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2019-08-08
  • Python實(shí)現(xiàn)Socket.IO的在線游戲場(chǎng)景方式

    Python實(shí)現(xiàn)Socket.IO的在線游戲場(chǎng)景方式

    本文介紹了Socket.IO的基本概念、應(yīng)用場(chǎng)景,并通過一個(gè)簡(jiǎn)單的多人在線實(shí)時(shí)對(duì)戰(zhàn)游戲案例,展示了如何使用Python和Socket.IO庫實(shí)現(xiàn)實(shí)時(shí)通信,Socket.IO的核心是事件驅(qū)動(dòng)模型,支持WebSocket協(xié)議,并在不支持的情況下回退到其他傳輸方式
    2025-01-01
  • 實(shí)例詳解Python裝飾器與閉包

    實(shí)例詳解Python裝飾器與閉包

    閉包是Python裝飾器的基礎(chǔ)。要理解閉包,先要了解Python中的變量作用域規(guī)則。本文主要給大家介紹Python裝飾器與閉包的相關(guān)知識(shí),需要的朋友可以參考下
    2019-07-07
  • Python使用Srapy框架爬蟲模擬登陸并抓取知乎內(nèi)容

    Python使用Srapy框架爬蟲模擬登陸并抓取知乎內(nèi)容

    這里我們來看如何通過Python使用Srapy框架爬蟲模擬登陸并抓取知乎內(nèi)容的實(shí)例,要實(shí)現(xiàn)持續(xù)的爬取需要利用到cookie的保存,我們首先還是來回顧一下cookie的相關(guān)知識(shí)點(diǎn):
    2016-07-07
  • Python腳本如何在bilibili中查找彈幕發(fā)送者

    Python腳本如何在bilibili中查找彈幕發(fā)送者

    這篇文章主要介紹了如何在bilibili中查找彈幕發(fā)送者,本文給大家分享小編寫的一個(gè)python腳本來實(shí)現(xiàn)bilibili彈幕發(fā)送者,需要的朋友可以參考下
    2020-06-06
  • Python字符串拼接六種方法介紹

    Python字符串拼接六種方法介紹

    這篇文章主要介紹了Python字符串拼接六種方法介紹,具有一定借鑒價(jià)值,需要的朋友看可以參考下。
    2017-12-12

最新評(píng)論

石渠县| 枞阳县| 电白县| 青河县| 周宁县| 儋州市| 嘉定区| 织金县| 洪江市| 旬阳县| 子洲县| 纳雍县| 吐鲁番市| 龙州县| 潮安县| 修文县| 呼图壁县| 凤凰县| 上栗县| 昆明市| 舞钢市| 武宁县| 稷山县| 泾川县| 家居| 丹阳市| 汉川市| 沙河市| 志丹县| 滁州市| 龙里县| 玉溪市| 桃园市| 新竹县| 饶河县| 普宁市| 灵寿县| 任丘市| 山阴县| 白河县| 象州县|