def sift_extract(X_train, n_features=3): print('SIFT based extraction has been started...') X_desc = [] # Extract descriptors for training images surf = cv2.xfeatures2d.SIFT_create() descriptors = [] for x in X_train: kp, des = surf.detectAndCompute(x['bbox_img'], None) descriptors.append(des) # Create BOW dictionary BOW = cv2.BOWKMeansTrainer(n_features) for dsc in descriptors: if dsc is not None: BOW.add(dsc) dictionary = BOW.cluster() bowDictionary = cv2.BOWImgDescriptorExtractor(surf, cv2.BFMatcher(cv2.NORM_L2)) bowDictionary.setVocabulary(dictionary) # Determine features for each image for x in X_train: features = surf.detect(x['bbox_img']) res = [0.987] * n_features if features is not None: r = bowDictionary.compute(x['bbox_img'], features) if r is not None: res = list(r[0]) X_desc.append(res) print('SIFT based extraction is done...') return np.matrix(X_desc)
def pen_detector(): pos, neg = "pos_", "neg_" detect, extract = get_extract_detect() matcher = get_flann_matcher() print("building BOWKMEANSTraniner...") bow_kmeans_trainer = cv2.BOWKMeansTrainer(27) extract_bow = cv2.BOWImgDescriptorExtractor(extract, matcher) print("adding features to trainer") for i in range(4): print(i) bow_kmeans_trainer.add(extract_sift(path(pos, i), extract, detect)) bow_kmeans_trainer.add(extract_sift(path(neg, i), extract, detect)) voc = bow_kmeans_trainer.cluster() extract_bow.setVocabulary(voc) traindata, trainlabels = [], [] print("adding to train data") for i in range(7): print(i+1) traindata.extend(bow_features(cv2.imread(path(pos, i), 0), extract_bow, detect)) trainlabels.append(1) traindata.extend(bow_features(cv2.imread(path(neg, i), 0), extract_bow, detect)) trainlabels.append(-1) svm = cv2.ml.SVM_create() svm.setType(cv2.ml.SVM_C_SVC) svm.setGamma(0.4) svm.setC(60) svm.setKernel(cv2.ml.SVM_LINEAR) svm.train(np.array(traindata), cv2.ml.ROW_SAMPLE, np.array(trainlabels)) return svm, extract_bow
def car_detector(): # 正例和反例前缀 pos, neg = "pos-", "neg-" # 获取特征检测和提取器实例 detect, extract = get_extract_detect() # 获取FLANN匹配器对象 matcher = get_flann_matcher() # 输出处理步骤1 print "1. building BOWKMeansTrainer..." # 创建基于词袋(BOW)的K-Means训练器,K = 12 bow_kmeans_trainer = cv2.BOWKMeansTrainer(12) # 获取BOW特征提取器 extract_bow = get_bow_extractor(extract, matcher) # 输出处理步骤2 print "2. adding features to trainer" # 将所有样本图像的特征添加到训练器中 for i in range(SAMPLES): print i bow_kmeans_trainer.add(extract_sift(path(pos, i), extract, detect)) # 调用BOW K-Means训练器的聚类函数生成样本图像的视觉词汇 vocabulary = bow_kmeans_trainer.cluster() # 将视觉词汇提供给BOW特征提取器 extract_bow.setVocabulary(vocabulary) # 定义数组,分别用来存储从训练图像中提取的BOW特征和相应的标签 traindata, trainlabels = [], [] # 输出处理步骤 3 print "3. adding to train data" # 使用样本图像的BOW特征填充训练数据数组及其标签(正例为1,反例为-1) # 从而将训练数据和类进行关联 for i in range(SAMPLES): print i # 增加一个正样本,设置标签为1 bf = bow_features(cv2.imread(path(pos, i), 0), extract_bow, detect) print bf traindata.extend(bf) trainlabels.append(1) # 增加一个负样本,设置标签为-1 bf = bow_features(cv2.imread(path(neg, i), 0), extract_bow, detect) print bf traindata.extend(bf) trainlabels.append(-1) # 创建SVM支持向量机进行分类训练 svm = cv2.ml.SVM_create() # 设置支持向量机的类型 svm.setType(cv2.ml.SVM_C_SVC) # 设置Gamma值 svm.setGamma(1) # 设置训练误差和预测误差 svm.setC(35) # 设置分类器的核函数,这里使用SVM_RBF(基于高斯函数的Radial Basis Function) svm.setKernel(cv2.ml.SVM_RBF) # 使用训练数据及其标签进行训练 svm.train(np.array(traindata), cv2.ml.ROW_SAMPLE, np.array(trainlabels)) # 返回训练好的SVM和BOW提取器对象 return svm, extract_bow
def initialize(self, image_data): """ Initializes the bag of words descriptor and returns the mapped results of image_data :param image_data: ndarray [n, 3D image] :return: list [label, [1D image descriptor]] """ termination_criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 30, 0.1) bow_model = cv2.BOWKMeansTrainer(self._num_clusters, termination_criteria) key_point_tensor = {} for i in range(image_data.shape[0]): cv_image = image_data[i] descriptors, key_points = BagOfFeaturesTransform.extract_features_descriptors(cv_image, self._patch_size) key_point_tensor[i] = key_points bow_model.add(descriptors[1]) self._clusters = bow_model.cluster() self._img_descriptor_mapper = cv2.BOWImgDescriptorExtractor(non_free.SURF_create(extended=True), cv2.FlannBasedMatcher_create()) self._img_descriptor_mapper.setVocabulary(self._clusters) training_x = [] for img_idx, img_descriptors in key_point_tensor.items(): image_quantized_descriptor = self._img_descriptor_mapper.compute(image_data[img_idx], img_descriptors) training_x.append(image_quantized_descriptor) return np.vstack(training_x)
def main(): ################################################## #detector = cv.xfeatures2d.SIFT_create() detector = cv.KAZE_create() matcher = cv.FlannBasedMatcher() bowTrainer = cv.BOWKMeansTrainer(100) bowExtractor = cv.BOWImgDescriptorExtractor(detector, matcher)
def build_extractor(xfeatures2d, dir_names=None, file_paths=None, dictionary_size=None, dictionary=None): if dir_names is not None and file_paths is not None: print('Computing descriptors..') BOW = cv2.BOWKMeansTrainer(dictionary_size) num_files = len(file_paths) bar = progressbar.ProgressBar(maxval=num_files).start() for i in range(num_files): p = file_paths[i] image = cv2.imread(p) gray = cv2.cvtColor(image, cv2.cv2.IMREAD_GRAYSCALE) kp, dsc = xfeatures2d.detectAndCompute(gray, None) BOW.add(dsc) bar.update(i) bar.finish() print('Creating BoW vocabs using K-Means clustering with k={}..'. format(dictionary_size)) dictionary = BOW.cluster() if dictionary is not None: print "bow dictionary", np.shape(dictionary) extractor = cv2.BOWImgDescriptorExtractor(xfeatures2d, cv2.BFMatcher(cv2.NORM_L2)) extractor.setVocabulary(dictionary) return extractor, dictionary
def detector(): detect, extract = get_extract_detect() matcher = get_flann_matcher() extract_bow = get_bow_extractor(extract, matcher) print "building BOWKMeansTrainer..." bow_kmeans_trainer = cv2.BOWKMeansTrainer(36) trainPosList, _ = globSplit(POS_PATH, SPLIT_NUMBER) trainNegList, _ = globSplit(NEG_PATH, SPLIT_NUMBER) print "adding features to trainer" # 给bow添加词汇信息 for jpg_file in trainPosList: print jpg_file bow_kmeans_trainer.add(extract_sift(jpg_file, extract, detect)) for jpg_file in trainNegList: print jpg_file siftData = extract_sift(jpg_file, extract, detect) if type(siftData) != NONE_TYPE: bow_kmeans_trainer.add(siftData) # 生成词汇,并设置词汇 vocabulary = bow_kmeans_trainer.cluster() extract_bow.setVocabulary(vocabulary) print "adding to train data" imageList = ['./images/demo.jpg'] print imageList for i in range(len(imageList)): imagePath = imageList[i] im = cv2.imread(imagePath) ssList = getSelectiveSelectRect(im) ssList = NMS(ssList, 0.2) for detectorItem in detectorList: print detectorItem ssListNew = [] testdata = [] mlp = joblib.load(detectorItem['cache']) for ssArea in ssList: crop_img = im[ssArea[1]:ssArea[3], ssArea[0]:ssArea[2]] crop_img = cv2.resize(crop_img, DEST_SIZE, interpolation=cv2.INTER_CUBIC) featureData = None if detectorItem['name'] == 'sift': featureData = bow_features(crop_img, extract_bow, detect) elif detectorItem['name'] == 'lbp': featureData = getLbpData(crop_img) if type(featureData) != NONE_TYPE: testdata.extend(featureData) ssListNew.append(ssArea) predict_proba = mlp.predict_proba(np.array(testdata)) predictData = [] for j in range(len(ssListNew)): ssRect = ssListNew[j] if predict_proba[j][1] > 0.5: ssListNew[j][4] = predict_proba[j][1] predictData.append(ssListNew[j]) showReuslt(im, predictData, detectorItem['color'])
def create_dictionary(): vocabulary = None paths = [ path for path in glob.iglob(IMAGES_DIR + '/*.jpeg') if path.split('-')[1] == '2' ] NUM_SAMPLES = int(len(paths) / 10) print('Gathering vocabulary from {} files'.format(NUM_SAMPLES)) for n, path in enumerate(random.sample(paths, NUM_SAMPLES)): print('Percent completed: {}\r'.format(int(n / NUM_SAMPLES * 100)), end='') _, des = describe(path) if vocabulary is None: vocabulary = des else: vocabulary = np.concatenate((vocabulary, des)) print('Descriptors gathered: {}'.format(vocabulary.shape[0])) dictionary_size = 200 tc = (cv2.TERM_CRITERIA_MAX_ITER, 100, 0.001) retries = 1 flags = cv2.KMEANS_PP_CENTERS print('Building dictionary', end='') trainer = cv2.BOWKMeansTrainer(dictionary_size, tc, retries, flags) dictionary = trainer.cluster(vocabulary) print(' completed') return dictionary
def train_bowextractor(cluster_count=40, extractor=cv2.xfeatures2d.SIFT_create(), matcher=cv2.FlannBasedMatcher()): ''' 该函数用于训练BOW特征提取器 :param cluster_count: 聚类个数,即词袋中单词种类数 :param extractor: 特征提取器,如ORB、SIFT、SURF等 :param matcher: 特征匹配器,如FLANNMatcher :return: 第一个返回值为“视觉单词”(K均值聚类出的中心),第二个返回值为BOW特征提取器 ''' pos, neg = "pos-", "neg-" print("building BOWKMeansTrainer...") bow_kmeans_trainer = cv2.BOWKMeansTrainer(cluster_count) extract_bow = cv2.BOWImgDescriptorExtractor(extractor, matcher) print("adding features to bow k-means trainer") start = time.time() for i in range(SAMPLES): kpts, sift_pos = extractor.detectAndCompute(cv2.imread(path(pos, i), cv2.IMREAD_GRAYSCALE), mask=None) if sift_pos is not None: bow_kmeans_trainer.add(sift_pos) kpts, sift_neg = extractor.detectAndCompute(cv2.imread(path(neg, i), cv2.IMREAD_GRAYSCALE), mask=None) if sift_neg is not None: bow_kmeans_trainer.add(sift_neg) vocabulary = bow_kmeans_trainer.cluster() print("Vocabulary Shape:", vocabulary.shape) # (cluster_count, 128) extract_bow.setVocabulary(vocabulary) end = time.time() print("训练BOW时间:", (end - start)) return vocabulary, extract_bow
def create_bow(datasets, vocab_size=100): """ Get the BOW vector for datasets :param datasets: List of dataset, [data] :param vocab_size: Number of features to extract :return:BOW vector for each dataset [[nbImage,nbVocab]] """ name = "vocab{}-{}-{}".format(vocab_size, datasets[0].shape[0], datasets[1].shape[0]) sift = cv2.xfeatures2d.SIFT_create() if os.path.exists("obj/{}.pkl".format(name)): vocab = load_obj(name) else: bow_km = cv2.BOWKMeansTrainer(vocab_size) for img in tqdm(np.concatenate(datasets)): h = sift.detectAndCompute(img, None) if h[1] is not None: bow_km.add(np.array(h[1])) vocab = bow_km.cluster() save_obj(vocab, name) bow = cv2.BOWImgDescriptorExtractor(sift, cv2.BFMatcher(cv2.NORM_L2)) bow.setVocabulary(vocab) bows = [] for data in datasets: acc = [] for img in tqdm(data): key, d = sift.detectAndCompute(img, None) desc = bow.compute(img, key) if desc is None: acc.append(np.zeros([vocab_size])) else: acc.append(desc[0]) bows.append(np.asarray(acc)) return bows
def train_vocabulary(self, train_file): self.trainfile = train_file self.bow_trainer = cv.BOWKMeansTrainer(VOCABULARY_SIZE) self.counter = 0 lines = calculate_lines(self.trainfile) self.max_lines = lines self.counter = 0 current_line = 0 tms = [] window = 50 with open(self.trainfile) as f: if self.multi_thread: p = mp.Pool(8) print('Multithreading') p.map(self.process_vocabulary, f.readlines()) p.close() p.join() else: for line in f: self.process_vocabulary(line) print('Clustering Phase...', flush=True) vocabulary = self.bow_trainer.cluster() print('End of Phase...') self.store_vocabulary(vocabulary)
def build_vocabulary(self, training_set: List[str], feature_type: str = 'SIFT', vocabulary_size: int = 100, iterations: int = 100, epsilon: float = 1e-6): """Builds a dictionary by clustering all the descriptors in the training set using K-means. Args: training_set: Paths to the training images. feature_type: Feature extractor { SIFT, SURF, KAZE }. vocabulary_size: Number of clusters. iterations: Maximum number of iterations for K-means. epsilon: Stop K-means if an accuracy of epsilon is reached. """ print("\nBUILDING DICTIONARY") self._initialize_feature_extractor(feature_type) termination_criteria = (cv2.TERM_CRITERIA_MAX_ITER | cv2.TERM_CRITERIA_EPS, iterations, epsilon) words = cv2.BOWKMeansTrainer(vocabulary_size, termination_criteria) # Extract features print("\nComputing", feature_type, "descriptors...") time.sleep(0.1) # Prevents a race condition between tqdm and print statements. for path in tqdm(training_set, unit="image", file=sys.stdout): image = cv2.imread(path, cv2.IMREAD_GRAYSCALE) _, descriptor = self._feature_extractor.detectAndCompute(image, None) words.add(descriptor) # Build vocabulary time.sleep(0.1) # Prevents a race condition between tqdm and print statements. print("\nClustering descriptors into", vocabulary_size, "words using K-means...") self._vocabulary = words.cluster()
def create_BOW(self, descriptors): """Computes a Bag of Words with a set of descriptors.""" print "\n\nCreating BOW with size {0} with {1} descriptors.".format(self.size, len(descriptors)) bowTrainer = cv.BOWKMeansTrainer(self.size) # Convert the list of numpy arrays to a single numpy array npdescriptors = np.concatenate(descriptors) # an OpenCV BoW only takes floats as descriptors. convert if necessary if not npdescriptors.dtype == np.float32: npdescriptors = np.float32(npdescriptors) if Settings.G_DETAILED_CONSOLE_OUTPUT: print "Clustering BOW with Extractor {0} and Matcher {1}".format(self.dextractor, self.dmatcher) self.__BOWVocabulary = bowTrainer.cluster(npdescriptors) # need to convert vocabulary? if self.__BOWVocabulary.dtype != self.vocabularyType: self.__BOWVocabulary = self.__BOWVocabulary.astype(self.vocabularyType) print "BOW vocabulary creation finished." # Create the BoW descriptor self.__BOWDescriptor = cv.BOWImgDescriptorExtractor(cv.DescriptorExtractor_create(self.dextractor), cv.DescriptorMatcher_create(self.dmatcher)) self.__BOWDescriptor.setVocabulary(self.__BOWVocabulary)
def train_vocabulary(self, file_list, vocabulary_size): kmeans_trainer = cv2.BOWKMeansTrainer(vocabulary_size) for path_to_image in file_list: img = cv2.imread(path_to_image, 0) kp, des = self.detector.detectAndCompute(img, None) kmeans_trainer.add(des) return kmeans_trainer.cluster()
def __init__(self, type, image_set, trained_hash, testing_hash, trained_directory): self.testing_hash = testing_hash self.trained_directory = trained_directory if trained_hash is not None: self._hash = trained_hash + "_" + image_set[0].hash super().__init__(type, image_set) self.size = 0.01 self.bowsize = 4096 if self.type is FeatureType.FREAK: self.size = 0.001 matcher = self.initMatcher(type) self.initFeature(type) self.dictionary = None self.bow_extract = cv2.BOWImgDescriptorExtractor(self.extractor, matcher) self.bow_train = cv2.BOWKMeansTrainer(self.bowsize) #print(testing_hash) try: if(self.trained_directory is not None): dictfile = "cache/" + str(self.name) + "/" + self.trained_directory + "/" + trained_hash + "_dict.npy" else: dictfile = self.directory + self.hash + "_dict.npy" logging.debug(dictfile) self.dictionary = np.load(dictfile) #logging.debug("Loaded dict cache.") except FileNotFoundError: logging.debug("Could not load dict cache file for this feature.")
def __init__(self, local_descriptor='SIFT', dictionary_size=5): if local_descriptor == 'SIFT': self._feature_detector = cv2.xfeatures2d.SIFT_create() logger.info("Initialized SIFT detector") FLANN_INDEX_KDTREE = 0 index_params = dict(algorithm=FLANN_INDEX_KDTREE, trees=5) elif local_descriptor == 'ORB': self._feature_detector = cv2.ORB_create() logger.info("Initialized ORB detector") FLANN_INDEX_LSH = 6 index_params = dict(algorithm=FLANN_INDEX_LSH, table_number=6, # 12 key_size=12, # 20 multi_probe_level=1) # 2 else: logger.error("Invalid local descriptor {}, defaulting to SIFT".format(local_descriptor)) self._feature_detector = cv2.xfeatures2d.SIFT_create() FLANN_INDEX_KDTREE = 0 index_params = dict(algorithm=FLANN_INDEX_KDTREE, trees=5) # global image descriptor self._dictionary_size = dictionary_size self._bow = cv2.BOWKMeansTrainer(self._dictionary_size) # feature matcher search_params = dict(checks=50) # or pass empty dictionary self._feature_matcher = cv2.FlannBasedMatcher(index_params, search_params) logger.info("Initialized FeatureProcessor")
def main(): parser = argparse.ArgumentParser() parser.add_argument('-i', '--input_dir', default=str(Path(__file__).parent / 'val2017')) parser.add_argument('-o', '--output_dir', default=str(Path(__file__).parent)) parser.add_argument('-n', '--num_cluster', type=int, default=50) args = parser.parse_args() detector = cv2.KAZE_create() bow_trainer = cv2.BOWKMeansTrainer(args.num_cluster) logger.info('Detect features') paths = list(Path(args.input_dir).glob('*')) for path in tqdm(paths): gray_img = cv2.imread(str(path), 0) _, des = detector.detectAndCompute(gray_img, None) bow_trainer.add(des) logger.info('Cluster BOWTrainer') codebook = bow_trainer.cluster() logger.info('Save codebook') np.save(str(Path(args.output_dir) / 'codebook'), codebook)
def car_detector(): pos, neg = "pos-", "neg-" detect, extract = get_extract_detect() flann = get_flann_matcher() print("Building BOWKMeansTrainer...") bow_kmeans_trainer = cv2.BOWKMeansTrainer(500) extract_bow = cv2.BOWImgDescriptorExtractor(extract, flann) print("adding features to trainer") for i in range(SAMPLES): print(i) bow_kmeans_trainer.add(extract_sift(path(pos, i), extract, detect)) bow_kmeans_trainer.add(extract_sift(path(neg, i), extract, detect)) print("cluster and set vocabulary") voc = bow_kmeans_trainer.cluster() extract_bow.setVocabulary(voc) traindata, trainlabels = [], [] print("adding to train data") for i in range(SAMPLES): print(i) traindata.extend(bow_features(cv2.imread(path(pos, i), 0), extract_bow, detect)) trainlabels.append(1) traindata.extend(bow_features(cv2.imread(path(neg, i), 0), extract_bow, detect)) trainlabels.append(-1) svm = cv2.ml.SVM_create() svm.setType(cv2.ml.SVM_C_SVC) svm.setGamma(0.5) svm.setC(30) svm.setKernel(cv2.ml.SVM_RBF) svm.train(np.array(traindata), cv2.ml.ROW_SAMPLE, np.array(trainlabels)) return svm, extract_bow
def train_vocabulary(imgs, detector, extractor, cluters=10): bow_kmeans_trainer = cv2.BOWKMeansTrainer(cluters) for img in imgs: description = extractor.compute(img, detector.detect(img))[1] if description is not None: bow_kmeans_trainer.add(description) voc = bow_kmeans_trainer.cluster() return voc
def carDetector(): """It is the function than use BOW extractor to give the method to train data. -------------- :return @svm: The trained SVM tool that can be used to make some predictions. @extract_bow: The BOW extractor, used to produce the descriptors of the corresponding images and key-points. The key-points can be gotten from the SIFT detector, using detect method. """ # 1. Create the SIFT detectors and extractors pos, neg = "pos-", "neg-" detect, extract = getExtractAndDetect() matcher = getFlannMatcher() print("Building BOWKMeansTrainer...") bow_kmeans_trainer = cv2.BOWKMeansTrainer(40) extract_bow = cv2.BOWImgDescriptorExtractor(extract, matcher) # 2. Cluster print("Adding features/descriptors to the trainer.") for i in range(int(conf.items("Sampling Data")[0][1])): # try: bow_kmeans_trainer.add(descriptorSift(path(pos, i), extract, detect)) bow_kmeans_trainer.add(descriptorSift(path(neg, i), extract, detect)) # except: # pass vocabulary = bow_kmeans_trainer.cluster() extract_bow.setVocabulary(vocabulary) # 3. Obtain the histogram (i.e. training data) of each image. train_data, train_labels = [], [] print("Adding to train data.") for i in range(int(conf.items("Sampling Data")[1][1])): try: train_data.extend( bowFeatures( cv2.imread(path(pos, i), flags=cv2.IMREAD_GRAYSCALE), extract_bow, detect)) train_labels.append(1) train_data.extend( bowFeatures( cv2.imread(path(neg, i), flags=cv2.IMREAD_GRAYSCALE), extract_bow, detect)) train_labels.append(-1) except: pass # 4. Train the SVM svm = cv2.ml.SVM_create() svm.setType(cv2.ml.SVM_C_SVC) svm.setGamma(0.5) svm.setC(30) svm.setKernel(cv2.ml.SVM_RBF) svm.train(np.array(train_data), cv2.ml.ROW_SAMPLE, np.array(train_labels)) return svm, extract_bow
def car_detector(cluster_count=40, extractor=cv2.xfeatures2d.SIFT_create(), matcher=cv2.FlannBasedMatcher()): ''' 该函数用于获取识别汽车的SVM分类器,以及BOW特征提取器 :param cluster_count: 聚类个数,即词袋中单词种类数 :param extractor: 特征提取器,如ORB、SIFT、SURF等 :param matcher: 特征匹配器,如FLANNMatcher :return: 第一个返回值为SVM分类器,第二个返回值为BOW特征提取器 ''' pos, neg = "pos-", "neg-" print("building BOWKMeansTrainer...") bow_kmeans_trainer = cv2.BOWKMeansTrainer(cluster_count) extract_bow = cv2.BOWImgDescriptorExtractor(extractor, matcher) print("adding features to trainer") start = time.time() for i in range(SAMPLES): kpts, sift_pos = extractor.detectAndCompute(cv2.imread(path(pos, i), cv2.IMREAD_GRAYSCALE), mask=None) if sift_pos is not None: bow_kmeans_trainer.add(sift_pos) kpts, sift_neg = extractor.detectAndCompute(cv2.imread(path(neg, i), cv2.IMREAD_GRAYSCALE), mask=None) if sift_neg is not None: bow_kmeans_trainer.add(sift_neg) vocabulary = bow_kmeans_trainer.cluster() print("Vocabulary Shape:", vocabulary.shape) # (cluster_count, 128) extract_bow.setVocabulary(vocabulary) end = time.time() print("训练BOW时间:", (end - start)) traindata, trainlabels = [], [] print("adding to train data") start = time.time() for i in range(SAMPLES): # print(i) bowDes_pos = bow_features(cv2.imread(path(pos, i), cv2.IMREAD_GRAYSCALE), extract_bow, extractor) if bowDes_pos is not None: traindata.extend(bowDes_pos) trainlabels.append(1) bowDes_neg = bow_features(cv2.imread(path(neg, i), cv2.IMREAD_GRAYSCALE), extract_bow, extractor) if bowDes_neg is not None: traindata.extend(bowDes_neg) trainlabels.append(-1) svm = cv2.ml.SVM_create() svm.setType(cv2.ml.SVM_C_SVC) svm.setGamma(1) svm.setC(35) svm.setKernel(cv2.ml.SVM_RBF) svm.train(np.array(traindata), cv2.ml.ROW_SAMPLE, np.array(trainlabels)) end = time.time() print("训练SVM时间:", (end - start)) return svm, extract_bow, vocabulary
def fit(self, train_path, k): ''' 开始训练 args: train_path:训练集图片路径 我们使用的数据格式为 train_path/dog/dog.i.jpg train_path/cat/cat.i.jpg k:k-means参数k ''' self.train_path = train_path """ FLANN匹配(单应性匹配): 两幅图像中的一幅 出现投影畸变的时候,他们还能彼此匹配 参数algorithm用来指定匹配所使用的算法,可以选择的有LinearIndex、KTreeIndex、KMeansIndex、CompositeIndex和AutotuneIndex,这里选择的是KTreeIndex(使用kd树实现最近邻搜索) """ flann_params = dict(algorithm=1, tree=5) flann = cv2.FlannBasedMatcher(flann_params, {}) # 创建BOW训练器,指定k-means参数k 把处理好的特征数据全部合并,利用聚类把特征词分为若干类,此若干类的数目由自己设定,每一类相当于一个视觉词汇 bow_kmeans_trainer = cv2.BOWKMeansTrainer(k) pos = 'dog' neg = 'cat' # 指定用于提取词汇字典的样本数 length = 10 # 合并特征数据 每个类从数据集中读取length张图片(length个狗,length个猫),通过聚类创建视觉词汇 for i in range(length): pos_descriptor = self.sift_descriptor_extractor(self.path(pos, i)) neg_descriptor = self.sift_descriptor_extractor(self.path(neg, i)) bow_kmeans_trainer.add(pos_descriptor) bow_kmeans_trainer.add(neg_descriptor) # 进行k-means聚类,返回词汇字典 也就是聚类中心 voc = bow_kmeans_trainer.cluster() # 输出词汇字典 <class 'numpy.ndarray'> (40, 128) print(type(voc), voc.shape) # 初始化bow提取器(设置词汇字典),用于提取每一张图像的BOW特征描述 self.bow_img_descriptor_extractor = cv2.BOWImgDescriptorExtractor( self.descriptor_extractor, flann) self.bow_img_descriptor_extractor.setVocabulary(voc) # 创建两个数组,分别对应训练数据和标签,并用BOWImgDescriptorExtractor产生的描述符填充 # 按照下面的方法生成相应的正负样本图片的标签 1:正匹配 -1:负匹配 traindata, trainlabels = [], [] for i in range(20): # 这里取200张图像做训练 traindata.extend(self.bow_descriptor_extractor(self.path(pos, i))) trainlabels.append(1) traindata.extend(self.bow_descriptor_extractor(self.path(neg, i))) trainlabels.append(-1) # 创建一个SVM对象 self.svm = cv2.ml.SVM_create() # 使用训练数据和标签进行训练 self.svm.train(np.array(traindata), cv2.ml.ROW_SAMPLE, np.array(trainlabels))
def cluster(data_list, k): BOW = cv2.BOWKMeansTrainer(k) for data in data_list: BOW.add(data) dic = BOW.cluster() save_path = 'codebook_%d.txt' % k np.savetxt(save_path, dic, delimiter=',', fmt='%1.4f') return dic
def get_bow(size, extract, matcher): """ size: 训练容器大小 extract: 特征检测方法 matcher : 特征匹配方法 创建BOW训练容器,BOW方法 """ return cv2.BOWKMeansTrainer(size), cv2.BOWImgDescriptorExtractor( extract, matcher)
def build_cv2(self): self.detector = cv2.FeatureDetector_create(self.detector_type) self.extractor = cv2.DescriptorExtractor_create(self.extractor_type) self.matcher = cv2.DescriptorMatcher_create(self.matcher_type) self.bow_extractor = cv2.BOWImgDescriptorExtractor(self.extractor, self.matcher) self.bow_trainer = cv2.BOWKMeansTrainer(clusterCount=self.num_cluster) if 'voc' in dir(self): self.bow_extractor.setVocabulary(self.voc)
def train(self, train_files, train_labels, k=33): """ Train :param train_files: :param train_labels: :param k: 33 or 34 or bigger? (better) """ # Create a BOW trainer print("Training with", len(train_files), "files") # criteria indicates the mode of iteration stop # eps --- precision 0.1 # max_iter --- meet more than the maximum number of iterations 20 criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 20, 0.1) # argument k for k-means bow_trainer = cv2.BOWKMeansTrainer(clusterCount=k) bar_widgets = [ 'SIFT Progress: ', Percentage(), '\t', Bar('#'), '\t', Timer(), '\t', ETA() ] bar = ProgressBar(widgets=bar_widgets, maxval=len(train_files)).start() for i in range(len(train_files)): bow_trainer.add(self.sift_descriptor(train_files[i])) bar.update(i) bar.finish() print("K-means cluster descriptors to vocabulary...") vocab = bow_trainer.cluster() print("K-means Done!") self.bow_extractor.setVocabulary(vocab) bar_widgets = [ 'BOW Progress: ', Percentage(), '\t', Bar('#'), '\t', Timer(), '\t', ETA() ] bar = ProgressBar(widgets=bar_widgets, maxval=len(train_files)).start() train_bow = [] for i, img in enumerate(train_files): train_bow.extend(self.bow_descriptor(img)) bar.update(i) bar.finish() # Use SVM for training print("Training SVM...") self.svm.train(np.asarray(train_bow), cv2.ml.ROW_SAMPLE, train_labels) # cv2.ml svm # self.svm.fit(np.asarray(train_bow), train_labels) # sklearn svm print("Scene Classifier Training Done!")
def __init__ (self,threshold,cluster_num): self.image_paths = [] self.image_keypoints = {} self.surf = cv2.xfeatures2d.SURF_create(threshold) self.bow_kmeans = cv2.BOWKMeansTrainer(cluster_num) self.bow_extractor = cv2.BOWImgDescriptorExtractor(self.surf, cv2.BFMatcher(cv2.NORM_L2)) self.empty_histogram = [0.0] * cluster_num self.count = 0
def make_codebook(images, code_book_size, save_name): bow_trainer = cv2.BOWKMeansTrainer(code_book_size) for img in images: f = calc_feature(img) # 特徴量計算 bow_trainer.add(f) code_book = bow_trainer.cluster() np.savetxt(save_name, code_book)
def build_codebook(input_dir, output_path, alg='sift', vocab_size=240, verbose=False): """Build the codebook (dictionary) for all the images in input dir. :param input_dir: The input directory containing all the images. :type input_dir: str :param output_path: The codebook output path. :type output_path: str :param alg: The feature detection & description algorithm (SIFT/KAZE). :type alg: str :param vocab_size: The vocabulary size (the number of clusters). :type vocab_size: int :param verbose: Show the status every 1% of total images. :type verbose: bool """ if alg.lower() == 'sift': detector = cv2.xfeatures2d.SIFT_create() elif alg.lower() == 'kaze': detector = cv2.KAZE_create() else: print 'Unknown algorithm. Option: sift | kaze' return bow = cv2.BOWKMeansTrainer(vocab_size) # Read images for root, dirnames, filenames in os.walk(input_dir): if verbose: print 'Extracting descriptors of images in: %s ...' % root n_images = len(filenames) filenames = fnmatch.filter(filenames, '*.[Jj][Pp][Gg]') for index, filename in enumerate(filenames): n_chunk = int(round(float(n_images) / 100)) n_chunk = 1 if n_chunk == 0 else n_chunk if index % n_chunk == 0 and verbose: print 'Processed: %s %% of images' % (index * 100 / n_images) # Get the descriptors image_path = os.path.join(root, filename) image = cv2.imread(image_path) gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY) keypoints, descriptors = detector.detectAndCompute(gray, None) bow.add(descriptors) # Cluster all the descriptors and save it into output file if verbose: print 'Clustering all the descriptors...' codewords = bow.cluster() codebook_file = open(output_path, 'wb') pickle.dump(codewords, codebook_file) return codewords
def obj_detector(): cep = 'cep_ind/cep_ind-' koljeno = 'kolj_ind/kolj_ind-' detect, extract = get_extract_detect() matcher = get_flann_matcher() print 'Building BOWKMeansTrainer ...' bow_kmeans_trainer = cv2.BOWKMeansTrainer(2048) extract_bow = get_bow_extractor(extract, matcher) print 'Adding features to trainer ...' for i in xrange(SAMPLES): print 'Adding image couple {}'.format(i + 1) bow_kmeans_trainer.add(extract_des(path(cep, i), extract, detect)) bow_kmeans_trainer.add(extract_des(path(koljeno, i), extract, detect)) print 'Number of features in BOW: {}'.format( bow_kmeans_trainer.descriptorsCount()) print 'Clustering features ...' voc = bow_kmeans_trainer.cluster() print 'Saving BOW vocabulary ...' fs = cv2.FileStorage('bow_vocabulary_ind.xml', cv2.FileStorage_WRITE) fs.write('bow-vocabulary-ind', voc) fs.release() # print 'Loading BOW vocabulary from file ...' # fs = cv2.FileStorage('bow_vocabulary.xml', cv2.FileStorage_READ) # node = fs.getNode('bow-vocabulary') # voc = node.mat() # fs.release() print 'Setting BOW vocabulary into extractor ...' extract_bow.setVocabulary(voc) traindata, trainlabels = [], [] print 'Adding to train data' for i in xrange(SAMPLES): print 'Adding image couple {}'.format(i + 1) traindata.extend( bow_features(cv2.imread(path(cep, i), 0), extract_bow, detect)) trainlabels.append(1) traindata.extend( bow_features(cv2.imread(path(koljeno, i), 0), extract_bow, detect)) trainlabels.append(2) svm = cv2.ml.SVM_create() svm.setType(cv2.ml.SVM_C_SVC) # svm.setGamma(2**-1) # svm.setNu(0.5) svm.setC(2**8) svm.setKernel(cv2.ml.SVM_INTER) print 'Training and saving SVN ...' svmTrainData = cv2.ml.TrainData_create(np.array(traindata), cv2.ml.ROW_SAMPLE, np.array(trainlabels)) svm.train(svmTrainData) svm.save('svm_data_ind.xml') return svm, extract_bow