直方图构建图像搜索引擎二

Hobbits and Histograms – A How-To Guide to Building Your First Image Search Engine in Python(直方图构建图像搜索引擎二)

英文原文
直方图构建图像搜索引擎一
translator:aaron-clark-aic

如何建立第一个Python图像搜索引擎

前面一章我们已经建立了基于色彩统计的彩色直方图。原作者的数据库中包含了25张对比图片(取材于霍比特人),我直接在百度上面找几张替代这些原数据。使用一个图像描述器来定义一张图像,图像描述器的输出是一个特征向量。使用两个特征向量进行比较就能够得到距离矩阵(前一篇文中提到的卡方分布Chi-squared)。

第一步:描述一个RGB的三通道图像

前一篇我们使用了一个RGB图像的32份粒度的三通道彩色直方图。

# load the image and show it
image = cv.imread(".././img/base.jpg")
# cv.imshow("image", image)

# grab the image channels, initialize the tuple of colors,
# the figure and the flattened feature vector
chans = cv.split(image)

hist3 = cv.calcHist([chans[0], chans[1], chans[2]], [0, 1, 2],
	None, [32, 32, 32], [0, 255, 0, 255, 0, 255])

flatten_base = hist3.flatten()

第二步: 编撰备选图像数据库的索引

index = {}
for imagePath in list_images(".././img/imgDataset"):
	# extract our unique image ID (i.e. the filename)
	k = imagePath[imagePath.rfind("/") + 1:]

	# load the image, describe it using our RGB histogram
	# descriptor, and update the index
	image_i = cv.imread(imagePath)
	chans = cv.split(image_i)

	hist3 = cv.calcHist([chans[0], chans[1], chans[2]], [0, 1, 2],
						None, [32, 32, 32], [0, 255, 0, 255, 0, 255])
	features = hist3.flatten()
	index[k] = features

第三步:查找

def chi2_distance( histA, histB, eps=1e-10):
	# compute the chi-squared distance
	d = 0.5 * np.sum([((a - b) ** 2) / (a + b + eps)
					  for (a, b) in zip(histA, histB)])
	# return the chi-squared distance
	return d

results = {}
for (k, features) in index.items():
	# compute the chi-squared distance between the features
	# in our index and our query features -- using the
	# chi-squared distance which is normally used in the
	# computer vision field to compare histograms
	d = chi2_distance(features, flatten_base)

	# now that we have the distance between the two feature
	# vectors, we can udpate the results dictionary -- the
	# key is the current image ID in the index and the
	# value is the distance we just computed, representing
	# how 'similar' the image in the index is to our query
	results[k] = d

# sort our results, so that the smaller distances (i.e. the
# more relevant images are at the front of the list)
results = sorted([(v, k) for (k, v) in results.items()])

第四步:匹配结果

fig = plt.figure()
ax = fig.add_subplot(711)
ax.set_title("base image")
ax.imshow(image)

for j in range(0,3):
	(score, imageName) = results[j]
	path = os.path.join(".././img/", imageName)
	result = cv.imread(path)
	print("\t{}. {} : {:.3f}".format(j + 1, imageName, score))
	index_i = 714+2*j-1
	ax = fig.add_subplot(str(index_i))
	ax.set_title(str((score, imageName)))
	ax.imshow(result)

第五步:代码下载

直方图构建图像搜索引擎二
完整代码下载链接