如何在OpenCV Python中匹配图像形状?
我们使用 cv2.matchShapes() 函数来匹配两个图像形状。该函数返回一个度量标准,显示图像形状之间的相似性。该函数使用Hu矩来计算度量值。度量值越低,图像形状之间的相似性就越高。
在以下示例中,我们将匹配来自不同图像的形状以及单个图像中的形状。
语法
我们使用以下语法来匹配两个图像形状-
其中,
- cnt1 - 第一个图像形状的轮廓点
-
cnt2 - 第二个图像形状的轮廓点
步骤
您可以使用以下步骤来匹配两个图像形状-
导入所需的库。在所有以下Python示例中,所需的Python库都是 OpenCV 。请确保您已经安装了它。
使用 cv2.imread() 将输入图像作为灰度图像读取。
在灰度图像上应用阈值处理,以创建二进制图像。
在二进制图像中查找形状的轮廓,使用 cv2.findContours() 函数。
从每个图像中选择特定的轮廓,并应用形状匹配函数 cv2.matchShapes() 传递所选择的轮廓。
打印结果值,即图像形状匹配度量。值越低,匹配越好。
让我们看一些例子,以便更好地理解。
示例1
在此程序中,我们匹配两个图像形状。每个图像都包含一个单一形状。我们还将从每个图像中匹配形状与自身的形状。
将下面的图像视为上述程序中提到的输入图像 ‘ star.png ‘ 和 ‘ pentagon.png ‘。


输出
执行后,上述代码将产生以下输出:
示例 2
在本程序中,我们匹配图像中的形状。我们检测图像中的三个形状。
import cv2
import numpy as np
img = cv2.imread('convexhull.png')
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
ret,thresh = cv2.threshold(gray,100,255,0)
contours,hierarchy = cv2.findContours(thresh, cv2.RETR_TREE,cv2.CHAIN_APPROX_SIMPLE)
print("发现的形状数量:",len(contours))
for i, cnt in enumerate(contours):
M = cv2.moments(cnt)
x1, y1 = cnt[0,0]
img1 = cv2.drawContours(img, [cnt], -1, (0,255,255), 3)
cv2.putText(img1, f'形状:{i+1}', (x1, y1), cv2.FONT_HERSHEY_SIMPLEX, 0.6, (0, 255, 0), 2)
cnt1 = contours[0]
cnt2 = contours[1]
cnt3= contours[2]
ret11 = cv2.matchShapes(cnt1,cnt1,1,0.0)
ret12 = cv2.matchShapes(cnt1,cnt2,1,0.0)
ret23 = cv2.matchShapes(cnt2,cnt3,1,0.0)
ret31 = cv2.matchShapes(cnt3,cnt1,1,0.0)
print("第一种形状与自身的匹配度:", ret11)
print("第一种形状与第二种形状的匹配度:", ret12)
print("第二种形状与第三种形状的匹配度:", ret23)
print("第三种形状与第一种形状的匹配度:", ret31)
cv2.imshow("形状", img)
cv2.waitKey(0)
cv2.destroyAllWindows()
在这个程序中,我们将使用下面的图像和 输入文件 −

输出
执行上述代码后,将产生以下输出−
我们得到以下窗口,显示输出结果 −

基于上述结果,我们得出形状1与形状2更相似,而不是形状3。