通过欧几里得距离(或任何其他距离计算技术)基于提取的 SIFT 描述符估计两幅图像的相似度得分

Posted

技术标签:

【中文标题】通过欧几里得距离(或任何其他距离计算技术)基于提取的 SIFT 描述符估计两幅图像的相似度得分【英文标题】:Estimation of similarity score of two images based on extracted SIFT descriptors by Euclidean distance (or any other distance computational technique) 【发布时间】:2018-05-12 15:05:53 【问题描述】:

我已经使用 openCV python 计算了带有 python 2.7 的图像 A 和 B 的 SIFT 描述符。 图像 A 有 16X128 (=2048) 个描述符,图像 B 有 10X128 (=1280)。 现在我被卡住了,因为我不知道如何生成相似度分数。 如果你能帮助我,我将不胜感激。

分数或相似性术语是一对匹配描述符之间的度量(例如欧几里得距离)但是将图像中的 SIFT 描述符本身与另一个描述符进行比较是不可行的,因为您最终会在图像中使用多个 SIFT 描述符,并且它们的数量取决于您提取它们的方式,正如我之前提到的,图像 A 有 16X128 (=2048) 描述符,另一个有 1028。

在matlab VL-feat中,SCORE的实现如下:

[fa, da] = vl_sift(Image_a) ;
[fb, db] = vl_sift(Image_b) ;
[matches, scores] = vl_ubcmatch(da, db) ;

最后,我想计算冒名顶替者和真正的分数,然后我想计算 EER。

我想提请您注意,我不想使用以下任何方法:

    MATLAB 中的 VLfeat BoW(词袋)算法( Euclidean distance in sift ) 回复Interpreting score in SIFT

谢谢。

这就是我提取 SIFT 关键点和描述符的方式:

import cv2
def extractFeatures_SIFT(Imagelist):
    l = len(Imagelist)
    featurlist = []
    for img_path in Imagelist:
        img = img_path
        img = cv2.imread(img)
        sift = cv2.xfeatures2d.SIFT_create()
        (kps, descriptor) = sift.detectAndCompute(img, None)
        featurlist += [kps, descriptor]

    return featurlist

【问题讨论】:

您的总体想法是什么?您如何在这里定义“相似性”? @Micka,我的意思是相似性是一对匹配描述符之间的度量(例如欧几里得距离)但是将图像中的 SIFT 描述符本身与另一个描述符进行比较是不可行的,因为你最终会在图像中有多个 SIFT 描述符,它们的数量取决于您提取它们的方式,例如图像 A 有 16X128 (=2048) 个描述符,另一个有 1028 个。 @Micka , 在 matlab VL-feat 中,SCORE 的实现如下: ** [fa, da] = vl_sift(Image_a) ; [fb, db] = vl_sift(Image_b) ; [匹配,分数] = vl_ubcmatch(da, db) ; ** 最后,我想计算冒名顶替和真实分数,然后我想计算 EER。 【参考方案1】:

如果您尝试开发图像之间的差异函数,您可能应该查看 global 而不是 local 描述符(SIFT 是本地描述符)。例如,GIST 或 CENTRIST。

词袋(出于某种原因,您试图避开它 - 实际上是为什么?)可以被视为进一步采用相同的方法(它通过学习本地描述符的分布来构建全局描述符),但它也很多更昂贵并且需要一个训练阶段。

【讨论】:

【参考方案2】:

由于在不同图像中检测到的关键点不同,因此图像中的 SIFT 描述符的数量随不同图像而变化。在您的情况下,图像 A 有 16 个关键点,图像 B 有 10 个关键点。为每个关键点计算 128 个值的 SIFT 描述符,因此图像 A 和 B 分别得到总共 2048 和 1280 个描述符值。

请注意,2048 和 1280 不是描述符的数量,而是图像 A 和 B 的描述符中的值的数量。图像 A 有 16 个描述符,图像 B 有 10 个描述符。关键点和描述符的这种差异很常见,因为不同的图像具有不同数量的可以被检测为关键点的有趣点。

这种差异不会对查找它们之间的相似性造成问题,因为当您通过 BFMatcher 和 FlannBasedMatcher 等匹配函数传递描述符时,您只会获得仅组合两个图像中相同数量的描述符的描述符匹配。通常,匹配的长度将等于最短描述符的长度。(在您的情况下,您将获得 10 个匹配)

接下来,从这 10 个匹配项中,您必须使用 David G.Lowe 给出的 crosscheckratio test 删除不必要的近似匹配项,并仅过滤掉好的比赛。即使那样,您也可能有误报匹配。这些可以通过使用 homography 或任何其他自定义方法进一步删除,具体取决于图像和您的应用程序。

在所有这些过程之后,您将获得最终匹配。您可以使用最终匹配的数量作为通过设置阈值来测试两个图像之间的相似性的方法。如果最终匹配的数量高于设定的阈值,则图像相似。如果最终匹配的数量小于设置的阈值,则图像不同。

在您的情况下,即使在开始时,您也只能使用 10 个匹配项。因此,当您完成上述所有过程并过滤掉匹配项时,您将只剩下很少的最终匹配项,您无法设置合理的阈值来获得所需的结果。因此,您可能必须在开始时增加检测到的关键点的数量。

这可以通过在 contrastThreshold'(默认值 = 0.04)和 'edgeThreshold'(默认值 =10)中传递一个较低的值来实现strong>SIFT_create() 函数[对于 OpenCV 3]。您还可以通过在 'nFeatures' 参数中传递合适的值来限制关键点的数量。

或者,要增加关键点,您可以尝试其他算法,如 SURF、ORB、... 来检测关键点,然后使用这些关键点计算这些关键点的 SIFT 描述符

希望我的回答对你有所帮助。

【讨论】:

以上是关于通过欧几里得距离(或任何其他距离计算技术)基于提取的 SIFT 描述符估计两幅图像的相似度得分的主要内容,如果未能解决你的问题,请参考以下文章

将 K 平均聚类距离度量更改为堪培拉距离或 python 上的任何其他距离度量

计算没有上溢或下溢的 3D 欧几里得距离

networkx 通过欧几里得距离阈值构造图

计算两个python数组之间的欧几里得距离

计算欧几里得距离的python方法的精度有啥不同吗?

根据欧几里德距离创建围绕圆的等距点:MATLAB