python-opencv-SVM (-215:Assertion failed) !_descriptors.empty() in function ‘cv::BOWTrainer::add‘

今天对python使用svm过程中出现的问题进行一下记录
先将代码插入进来

import cv2
import numpy as np
from os.path import join

datapath = r"D:/BaiduNetdiskDownload/opencv/CarData/TrainImages"
def path(cls,i):
    return "%s/%s%d.pgm" % (datapath,cls,i+1)

pos, neg = "pos-","neg-"

detect = cv2.xfeatures2d.SIFT_create()
extract = cv2.xfeatures2d.SIFT_create()

flann_parms = dict(algorithm = 1,trees = 5)
flann = cv2.FlannBasedMatcher(flann_parms,{ })

bow_kmeans_trainer = cv2.BOWKMeansTrainer(40)
extract_bow = cv2.BOWImgDescriptorExtractor(extract, flann)

def extract_sift(fn):
    im = cv2.imread(fn,0)
    return extract.compute(im,detect.detect(im))[1]

for i in range(6):
    bow_kmeans_trainer.add(extract_sift(path(pos,i)))
    bow_kmeans_trainer.add(extract_sift(path(neg,i)))

voc = bow_kmeans_trainer.cluster()
extract_bow.setVocabulary(voc)

def bow_features(fn):
    im = cv2.imread(fn,0)
    return extract_bow.compute(im,detect.detect(im))

traindata, trainlabels = [], []
for i in range(20):
    traindata.extend(bow_features(path(pos,i)));
    trainlabels.append(1)
    traindata.extend(bow_features(path(neg,i)));
    trainlabels.append(-1)

svm = cv2.ml.SVM_create()
svm.train(np.array(traindata),cv2.ml.ROW_SAMPLE,np.array(trainlabels))

def predict(fn):
    f = bow_features(fn);
    p = svm.predict(f)
    print (fn, "/t",p[1][0][0])
    return p


car, notcar =r"D:/BaiduNetdiskDownload/opencv/car.jpg",r"D:/BaiduNetdiskDownload/opencv/2.png"# picture path
car_img = cv2.imread(car)
notcar_img = cv2.imread(notcar)
car_predict = predict(car)
not_car_predict = predict(notcar)

font = cv2.FONT_HERSHEY_DUPLEX

if (car_predict[1][0][0] == 1.0):
    cv2.putText(car_img,'Car Detected',(10,30),font,1,(0,255,
                0),2,cv2.LINE_AA)

if (not_car_predict[1][0][0]==-1.0):
    cv2.putText(notcar_img,'Car Not Detected',(10,30),font,1,(0,0,
                255),2,cv2.LINE_AA)

cv2.imshow('BOW+SVM Success',car_img)
cv2.imshow('BOW+SVM Failure',notcar_img)
cv2.waitKey(0)
cv2.destroyALLWindows()

首先出现的问题是路径问题,图片和训练集路径需要添加转转义符‘\’,或者将‘\’变成‘/’加入路径内。
例:D:/BaiduNetdiskDownload/opencv/car.jpg

出现的第二个问题:
OpenCV(3.4.2) C:\projects\opencv-python\opencv\modules\features2d\src\bagofwords.cpp:55: error: (-215:Assertion failed) !_descriptors.empty() in function ‘cv::BOWTrainer::add’
翻译后
fnOpenCV(3.4.2)C:\projects\opencv python\opencv\modules\feature2d\src\巴格沃兹。cpp:55:错误:(-215:断言失败)!_描述符。空()在函数“cv::BOWTrainer::add”中
是由语句traindata.extend(bow_features(path(pos,i)))引起的。
说来也惭愧,在遍寻资料后才发现,是路径出问题了,导致找不到数据集文件。
大致有以下几种情况:
1.由图片属性内路径复制过来,可能会出现转码问题,复制过来是一串字符,但是由于复制过来后由IDE转码显示,在读取路径时读取源码不成功。
2.路径内包含中文字符
3.路径内并没有符合要求的数据集。

第三个问题是由函数

def predict(fn):
    f = bow_features(fn);
    p = svm.predict(f)
    print (fn, "/t",p[1][0][0])
    return p

引起的,主要是因为路径内数据集不符合要求。

第四个问题是由FONT_HERSHEY_SIMPLEX引起的,这是opencv内置字体,当其报错时,是因为内部字体缺失,可以更换其他字体试一试。例:

CV_FONT_HERSHEY_SIMPLEX -               正常大小无衬线字体. 
CV_FONT_HERSHEY_PLAIN -                 小号无衬线字体.
CV_FONT_HERSHEY_DUPLEX -                正常大小无衬线字体比 CV_FONT_HERSHEY_SIMPLEX 更复杂) 
CV_FONT_HERSHEY_COMPLEX -               正常大小有衬线字体.
CV_FONT_HERSHEY_TRIPLEX -               正常大小有衬线字体 (  比 CV_FONT_HERSHEY_COMPLEX更复杂) 
CV_FONT_HERSHEY_COMPLEX_SMALL -          CV_FONT_HERSHEY_COMPLEX 的小译本.
CV_FONT_HERSHEY_SCRIPT_SIMPLEX -         手写风格字体.
CV_FONT_HERSHEY_SCRIPT_COMPLEX -         比 CV_FONT_HERSHEY_SCRIPT_SIMPLEX 更复杂.

参数能够由一个值和可选择的 CV_FONT_ITALIC 字体标记合成。就是斜体字.

参数vscale,和hscale分别表示行高、和字体宽度,当其值被设为1.0时,就为默认值,当其值被设为0.5时,就为原默认值的一半,shear参数表示字体的倾斜程度,当其值为0时,表示字体不倾斜,当其值为1时,文字倾斜45度.

最后要注意的是 SIFT 由专利法保护,在高版本中已经去除,如需使用,请安装低版本。具体方法见:from matplotlib import pyplot as plt 报错问题及matplotlib正确安装

你可能感兴趣的:(python-opencv,opencv,python)