如何在OpenCV Python中从特征匹配中获得像素坐标



我需要获得特征匹配器在提供的代码中选择的像素的xy坐标的列表。我正在使用Python和OpenCV。有人能帮我吗?

img1=cv2.imread('DSC_0216.jpg',0)
img2=cv2.imread('DSC_0217.jpg',0)
orb=cv2.ORB(nfeatures=100000)
kp1,des1=orb.detectAndCompute(img1,None)
kp2,des2=orb.detectAndCompute(img2,None)
img1kp=cv2.drawKeypoints(img1,kp1,color=(0,255,0),flags=0)
img2kp=cv2.drawKeypoints(img2,kp2,color=(0,255,0),flags=0)
cv2.imwrite('m_img1.jpg',img1kp)
cv2.imwrite('m_img2.jpg',img2kp)
bf=cv2.BFMatcher(cv2.NORM_HAMMING, crossCheck=True)
matches=bf.match(des1,des2)
matches=sorted(matches, key= lambda x:x.distance)

我们知道你的关键点存储在kp1kp2中,它们分别是第一个和第二个图像的特征匹配列表。在cv2.ORB透视图中,特征描述符是2D矩阵,其中每行是在第一张和第二张图像中检测到的关键点。

在你的例子中,因为你使用cv2.BFMatch, matches返回cv2.DMatch对象的列表,其中每个对象包含几个成员,其中有两个重要成员:

  • queryIdx -与
  • 匹配的kp1兴趣点矩阵的索引或
  • trainIdx -与
  • 匹配的kp2兴趣点矩阵的索引或

因此,queryIdxtrainIdx告诉您在第一个和第二个图像之间匹配哪些ORB特征。您可以使用这些来索引kp1kp2,并获得pt成员,这是一个由(x,y)坐标组成的元组,它确定了匹配的实际空间坐标。

你所要做的就是遍历matches中的每个cv2.DMatch对象,附加到kp1kp2的坐标列表,然后你就完成了。

像这样:

# Initialize lists
list_kp1 = []
list_kp2 = []
# For each match...
for mat in matches:
    # Get the matching keypoints for each of the images
    img1_idx = mat.queryIdx
    img2_idx = mat.trainIdx
    # x - columns
    # y - rows
    # Get the coordinates
    (x1, y1) = kp1[img1_idx].pt
    (x2, y2) = kp2[img2_idx].pt
    # Append to each list
    list_kp1.append((x1, y1))
    list_kp2.append((x2, y2))

请注意,我可以只做list_kp1.append(kp1[img1_idx].pt)list_kp2相同,但我想让它非常清楚如何解释空间坐标。您还可以更进一步,执行列表推导:

list_kp1 = [kp1[mat.queryIdx].pt for mat in matches] 
list_kp2 = [kp2[mat.trainIdx].pt for mat in matches]

list_kp1将包含与list_kp2中相应位置匹配的特征点的空间坐标。也就是说,list_kp1的元素i包含img1的特征点的空间坐标,与list_kp2img2对应的特征点的空间坐标在元素i中相匹配。


作为一个小旁注,我在为drawMatches编写解决方案时使用了这个概念,因为对于OpenCV 2.4。x中不存在c++函数的Python包装器,因此我利用上述概念定位两个图像之间匹配特征的空间坐标来编写我自己的实现。

如果你喜欢的话可以去看看!

模块# 39;drawMatches'opencv python

相关内容

  • 没有找到相关文章

最新更新