返回列表

5th Place Solution: Customized Scene Matching

611. Image Matching Challenge 2024 - Hexathlon | image-matching-challenge-2024

开始: 2024-03-25 结束: 2024-06-03 计算机视觉 数据算法赛
第五名方案:定制化场景匹配

第五名方案:定制化场景匹配

作者:Khoa Ngo
比赛:Image Matching Challenge 2024
排名:第5名

首先,感谢主办方第三次在Kaggle上组织图像匹配挑战赛。同时,向获胜者表示祝贺,并祝愿所有经历这次艰难旅程的人都平安顺利。

我承认我参加比赛的时间比较晚。因此,我只能凭"感觉"行事,临场发挥。所以,你可能会发现我的方案在某些方面有点巧妙 :))。让我们开始吧!

1. 概述

我的解决方案架构可以总结为下图:

架构图

我的总结分为四个主要部分:

  • 构建本地评估数据集
  • 构建通用SfM流程
  • 针对特定类别定制流程
  • 结果

2. 本地评估数据集

原始数据集显然太大且不切实际,无法用于评估。为了解决这个问题,我构建了3个版本的子集(通过采用一些随机采样策略)。这3个版本的结果高度相关。因此,我选择其中一个作为我的主要本地验证数据集:

数据集/场景 样本数量
Pond 100
Lizard 90
Church 80
Dioscuri 70
Multi-temporal-temple-baalshamin 68
Transp_obj_glass_cup 36
Transp_obj_glass_cylinder 36

我将在此数据集上报告我的本地交叉验证结果。

3. SfM流程

为了更好地解释,我将该流程分为3个模块:

  • 通过全局描述符提出候选图像对
  • 对候选列表中的图像对进行匹配
  • 使用Colmap进行重建

3.1 寻找候选图像对

我使用了来自timm的3个预训练模型来提取全局特征:

EVA-CLIP Base   
ConvNeXt Base    | -->[concat]--> [fc 2560]
Dinov2 ViT Base /

我还为不同类型的场景定制了相似度阈值(注意,我使用的是余弦相似度而不是距离)。例如,对于像Lizard这样的高度多样化场景,我使用了较低的阈值0.6。相反,对于像Cylinder和Cup这样的物体场景,较高的阈值0.95更合理。

3.2 图像匹配

延续我去年解决方案的精神,我只专注于基于检测器的方法,因为它们比半密集或密集模型轻量得多。由于缺乏CV和LB的实验,我无法给出每个方法的详细数字,只能大致说明它们的整体表现。以下是我在比赛中尝试的一些组合:

不知道为什么在LB上表现不好
方法 CV表现 LB表现 备注
SuperPoint + SuperGlue 不好 比LightGlue慢
GlueStick 一般 -
SuperPoint + LightGlue 非常好 不好
ALIKED + LightGlue 非常好 LB上最佳
DISK + LightGlue 一般
OmniGlue 不好 -

此外,我还尝试将SIFT + NN作为轻量级集成模型添加到LightGlue中。IMC23第七名方案声称将SIFT与LightGlue集成可以提升性能。我认为在某些场景的CV中确实如此,但它对LB结果造成了很大伤害(-0.03)。

总之,我想说LightGlue是目前图像匹配问题中最好的模型之一(向作者致敬)!

3.3 重建

今年我花了一些时间尝试更好地利用colmap,超越主办方的基线。以下是我的一些尝试:

  • 针对特定场景使用单相机:在本地CV中对透明物体场景效果很好,但会恶化LB结果。
  • 手动初始对:我选择了匹配数量和关键点最多的图像对,并将其设置为colmap的初始对。但它使我的CV结果变差了(也许是我的代码有问题?!!)。
  • 多次运行增量映射:它使我的CV结果更一致且略好。然而,我没有看到它对LB有任何影响。

很遗憾地说,我无法在colmap上做出任何明显的改进。

4. 针对特定类别的处理

4.1 透明物体

我认为这个类别决定了金牌。因为当我解决这个问题时,我立即从第300名跃升至第10名!!!

首先,我将展示如何创建这个解决方案的过程,希望会更生动 :)。

如果你打开一张图片,然后逐张移动到下一张,你会发现这就像是从一个相机拍摄的视频中截取的帧序列。

人类会如何匹配这些图片?如果是我,我会只聚焦在物体上,忽略整个背景。此外,我只需要匹配一个序列(或)的帧:(0, 1), (1, 2),...,(35, 0),这意味着不需要匹配(1, 20)或(3, 29)!

环匹配

通过在匹配cylinder之前添加这两行代码,我在CV上使用LightGlue从~0.0提升到了0.86

image = image[950:2850, :, :]
index_pairs = [(i, i+1) for i in range(len(scene)-1)] + [(len(scene)-1, 0)]

所以现在问题可以分解为两个更小的问题:

  • 检测物体
  • 找到最佳连续对

4.1.1 物体检测

方法1(无效):使用目标检测模型:我尝试了Yolo系列。不过,很难让模型找到精确的物体位置。

  • 方法1:使用Yolov8生成所有边界框 => 没有检测到任何框!
  • 方法2:使用YoloWorld关键词"transparent object" => 没有检测到任何东西。
  • 方法3:使用YoloWorld关键词"cup" => 可以检测到杯子。但它不够通用,无法应用于LB数据集。

方法2(最终解决方案):使用分割模型:

  • 步骤1:使用MobileSAM检测图像中的所有掩码。
  • 步骤2:使用上述关键点提取器(SuperPoint或ALIKED)提取物体关键点。背景中会产生一些噪声。
  • 步骤3:找到最佳掩码:包含最多关键点的最小掩码。
  • 步骤4:找到包含最佳掩码的最小边界框。

我也尝试了DBSCAN。然而,由于开发时间的限制,我没有最终完成它来看看它是否可以取代SAM。

SAM掩码

4.1.2 寻找最佳图像对

问题定义

  • 版本1:找到完美的图像序列。
  • 版本2(简化版):对于每张图片,找出另外两张最佳匹配图片。

方法1(不好):基于两帧之间像素移动最小的原理,我使用RAFT计算所有可能对的光流,然后获得平均幅度。我进一步结合上述全局嵌入的余弦相似度构建NxN矩阵:

pair_score[i, j] = -of_mag[i, j] + cos_sim[i, j]

TSP求解器无法产生完美的环(约90%准确率)。因此,我认为它不够好。

方法2(更简单但更好):我对所有图像对进行穷举匹配。然后,构建一个NxN矩阵,其元素是每对之间的匹配数量:

pair_score[i, j] = n_matches[i, j]

随后,我简单地选择每行中最大的两个值。这种简单的方法惊人地产生了接近100%的准确率(我尝试了不同的匹配器,有时会有1-2个错误的配对)。

4.2 昼夜

方法1:找出暗图像并增强它们。

暗检测非常容易,只需要找出均值小于阈值(可以是65、70)的图像。

我使用CLAHE来增强暗图像。不幸的是,它使我的LB分数降低了0.01。

方法2:使用DarkFeat匹配器。

我的想法是将LightGlue与一个对暗图像更鲁棒的匹配器集成。我发现DarkFeat可能是一个有前途的候选者。不幸的是,我没有看到使用它的任何好处。

4.3 对称性和重复

我认为这些场景由于其自然特性可能存在大量误匹配。

方法1:首先,我尝试使用更严格的参数进行调优(例如,将匹配阈值提高到0.5等)。尽管如此,它没有显示任何改进。

方法2:接下来,我转向一个更有前途的方法:Doppelgangers: Learning to Disambiguate Images of Similar Structures。这种方法的主要思想是:

  • 首先,运行一次SfM获取所有匹配对。
  • 使用Doppelganger模型过滤掉高概率为误报(伪装者)的配对。

它在本地CV的Church场景上没有显示任何改进。

所以基本上,我无法在这个类别上做出任何改进。

4.4 其他

剩余的类别包括自然场景、航拍ground、历史保护、时间序列。

实际上,很难定制这些场景,因为它们似乎太通用了。

因此,我只是应用了旋转检测方法来校正图像方向。它在本地CV的Dioscuri场景上产生了巨大提升,并在LB上增加了约+0.005。

5. 结果

交叉验证

场景 方法 结果
Pond ALIKED+LightGlue 0.46
Lizard SP+LightGlue 0.73
Church ALIKED+LightGlue 0.18
Dioscuri ALIKED+LightGlue 0.49
Multi-temporal-temple-baalshamin ALIKED+LightGlue 0.48
Transp_obj_glass_cup DISK+LightGlue 0.32
Transp_obj_glass_cylinder ALIKED+LightGlue 0.81

排行榜

方法 公开LB 私有LB
我的IMC23: SP+SG 0.104 0.111
SP+LG 0.099 0.115
SP+LG+rot 0.103 0.119
ALIKED+LG+rot 0.135 0.147
ALIKED+LG+rot+transparent_custom 0.18 0.19
ALIKED+LG+rot+transparent_custom+tuning 0.186 0.195
ALIKED+LG+rot+transparent_custom+tuning+dark_enhance 0.179 0.183

6. 结论

有趣的事实:我参加了Kaggle上的所有三届图像匹配挑战赛,并获得了三种不同颜色的奖牌 😂:

  • 2022年:铜牌🥉
  • 2023年:银牌 🥈
  • 2024年:金牌 🥇

参加这样艰难的比赛让我感到精疲力竭。但最终,经过不懈努力,甜蜜的果实终于来了 😁。

感谢你的阅读。希望你能从中找到一些有趣的内容。

快乐Kaggling!

同比赛其他方案