使用python+opecncv實作目标檢測
以下是需要用到的函數,請讀者在閱讀代碼時先行了解:
sift算法:此算法用于擷取關鍵點和秒數符
flann比對:用于比對不同的描述符
詞袋:bow
支援向量機:svm
import cv2 as cv
import numpy as np
def path(cls, i):
return "%s%s%d.jpg" % (datapath, cls, i)
def extract_Sift(fn):
image = cv.imread(fn, 0)
return extract.compute(image, detect.detect(image))[1]
def bow_xfeatures(fn):
image = cv.imread(fn, 0)
return bow_extract.compute(image, detect.detect(image))
def svm_predict(fn):
f = bow_xfeatures(fn)
p = svm.predict(f)
return p
datapath = "/home//feng/carimages/"
pos, neg = "pos-", "neg-" #全部的汽車照片都是有pos-x.jpg組成的,非汽車圖檔都是有neg-x.jpg組成的。
detect = cv.xfeatures2d.SIFT_create() #建立sift算法
extract = cv.xfeatures2d.SIFT_create()
indexpara = dict(algorithm=1, trees=5)
checkpara = dict(checks=50)
flann = cv.FlannBasedMatcher(indexpara, checkpara)
bow_trainer = cv.BOWKMeansTrainer(40) #定義一個40個族的詞袋
bow_extract = cv.BOWImgDescriptorExtractor(extract, flann)#sift用來提取特征,flann用來比對描述符
for i in range(1, 9):
bow_trainer.add(extract_Sift(path(pos, i)))
bow_trainer.add(extract_Sift(path(neg, i)))
voc = bow_trainer.cluster() #voc即是詞袋的初始“詞典”
bow_extract.setVocabulary(voc)
traindata, trainlabels = [], []
for i in range(1, 21):
traindata.extend(bow_xfeatures(path(pos, i)))#為不同的訓練資料定義不同标簽
trainlabels.append(1)
traindata.extend(bow_xfeatures(path(neg, i)))
trainlabels.append(-1)
svm = cv.ml.SVM_create() #建立支援向量機并用詞袋提取出來的描述符去訓練支援向量機
svm.train(np.array(traindata), cv.ml.ROW_SAMPLE, np.array(trainlabels))
car = "/home/feng/carimages/carimage.jpeg"
notcar = "/home/feng/carimages/notcarimage.jpg"
carimage = cv.imread(car)
notcarimage = cv.imread(notcar)
car_predict = svm_predict(car)
notcar_predict = svm_predict(notcar)
if car_predict[1][0][0] == 1.0:
cv.putText(carimage, "car_detected", (10, 30), cv.FONT_HERSHEY_SIMPLEX, 1, (0, 0, 255), 1, cv.LINE_AA)
if notcar_predict[1][0][0] == -1.0:
cv.putText(notcarimage, 'car_not_detecte', (10, 30), cv.FONT_HERSHEY_SIMPLEX, 1, (0, 0, 255), 1, cv.LINE_AA)
cv.imshow("car_Detect_demo", carimage)
cv.imshow("car_detect_Demo", notcarimage)
cv.waitKey(0)
cv.destroyAllWindows()
代碼的編寫模仿于由喬.米尼奇諾編寫的opencv3計算機視覺python實作。