在Python中尝试使用OpenCV的cv2.matchShapes()

6 投票
3 回答
11164 浏览
提问于 2025-04-18 02:21

我在白板上随便画了一个图,然后NAO机器人拍了一张照片,试着把这个图重新画出来。

我的画:

这里输入图片描述

NAO的画:

这里输入图片描述

现在我想写一些结论,特别是我想从这两张图片中提取轮廓,并使用OpenCVcv2.matchShapes()函数来匹配这些轮廓。

不过,我写了一个小的Python代码脚本来实现这个功能,但它给我报了一些错误。以下是代码:

import numpy as np
import cv2

#get the pictures from the forlder
original = cv2.imread('eightgon.jpg')
drawn = cv2.imread('eightgon1.jpg')

#make them gray    
originalGray = cv2.cvtColor(original, cv2.COLOR_BGR2GRAY)
drawnGray = cv2.cvtColor(drawn, cv2.COLOR_BGR2GRAY)

#apply erosion
kernel = np.ones((2, 2),np.uint8)
originalErosion = cv2.erode(originalGray, kernel, iterations = 1)
drawnErosion = cv2.erode(drawnGray, kernel, iterations = 1)

#retrieve edges with Canny
thresh = 175
originalEdges = cv2.Canny(originalErosion, thresh, thresh*2)
drawnEdges = cv2.Canny(drawnErosion, thresh, thresh*2)

#extract contours
originalContours, Orighierarchy = cv2.findContours(originalEdges, cv2.cv.CV_RETR_CCOMP, cv2.CHAIN_APPROX_SIMPLE)
drawnContours, Drawnhierarchy = cv2.findContours(drawnEdges, cv2.cv.CV_RETR_CCOMP, cv2.CHAIN_APPROX_SIMPLE)

print cv2.matchShapes(drawnContours,originalContours,cv2.cv.CV_CONTOURS_MATCH_I1, 0.0)

当我运行这段简单的代码时,它给我返回了这个错误:

File "C:/Python27/getResults.py", line 32, in <module>
    ret = cv2.matchShapes(drawnContours,originalContours,cv2.cv.CV_CONTOURS_MATCH_I1, 0.0)
TypeError: contour1 is not a numpy array, neither a scalar

因为错误提示我说轮廓应该是数组,所以我对代码做了一些小改动,变成这样:

cnt1 = np.asarray(drawnContours, np.int0)
cnt2 = np.asarray(originalContours, np.int0)
print cv2.matchShapes(cnt1,cnt2,cv2.cv.CV_CONTOURS_MATCH_I1, 0.0)

但这次它又给我返回了这个错误:ValueError: setting an array element with a sequence.

我到底哪里出错了呢?希望能得到一些帮助!

3 个回答

-3

检查一下你的opencv版本,旧版的可能在matchShapes或findContours的使用上和新版本不一样。

因为很遗憾,有些NAO软件的版本里包含了比较旧的opencv版本。

考虑更新你的NAO软件,或者试试获取一些测试版的软件……

2

这里的 drawnContoursoriginalContours 是图像中包含的轮廓列表。你可以用 drawnContours[i]originalContours[i] 来表示一个特定的轮廓,其中 i = 0,1,2...n-1,n 是图像中轮廓的总数。

举个例子,

print cv2.matchShapes(
    drawnContours[0], originalContours[0], 
    cv2.cv.CV_CONTOURS_MATCH_I1, 0.0)

要获取图像中轮廓的总数,可以使用:

n = len(drawnContours)  # n is the number of contours
print n
4

我遇到过类似的问题。这个匹配形状的函数只需要一对轮廓,而不是整个轮廓的容器对。

cv2.matchShapes(drawnContours[i], originalContours[i], cv2.cv.CV_CONTOURS_MATCH_I1, 0.0)

希望这能帮到你。

撰写回答