目标检测基础(NMS)
什么是非最大值抑制
非最大值抑制是一种主要用于目标检测的技术,旨在从一组重叠框中选择最佳边界框。在下图中,非最大值抑制的目的是删除黄色和蓝色框,这样我们只剩下绿色框作为最终的预测结果。
计算NMS的步骤
为了了解什么是boundingbox,以及IOU的含义,我在前篇发表了关于IOU的文章。前篇文章中描述的术语将在本文中继续介绍。
我们首先描述NMS在这个特定示例中的工作过程,然后解释一个更通用的算法,将其扩展到不同的场景下。
1、术语定义
我们将使用的每个边界框的格式如下:
b
o
x
_
l
i
s
t
=
[
x
1
,
??
y
1
,
??
x
2
,
??
y
2
,
??
c
l
a
s
s
??
c
o
n
f
i
d
e
n
c
e
]
box\_list=[x1,\ \ y1,\ \ x2,\ \ y2,\ \ class\ \ confidence]
box_list=[x1,??y1,??x2,??y2,??class??confidence] 让我们假设,对于上述这个特定的图像我们有3个边界框,即:
b
b
o
x
_
l
i
s
t
=
[
b
l
u
e
_
b
o
x
,
y
e
l
l
o
w
_
b
o
x
,
g
r
e
e
n
_
b
o
x
]
bbox\_list=[blue\_box,yellow\_box,green\_box]
bbox_list=[blue_box,yellow_box,green_box] 对于每个框,相关定义如下
b
l
u
e
_
b
o
x
=
[
x
3
,
??
y
3
,
??
x
4
,
??
y
4
,
??
"
C
a
t
"
??
0.85
]
y
e
l
l
o
w
_
b
o
x
=
[
x
5
,
??
y
5
,
??
x
6
,
??
y
6
,
??
"
C
a
t
"
??
0.75
]
g
r
e
e
n
_
b
o
x
=
[
x
1
,
??
y
1
,
??
x
2
,
??
y
2
,
??
"
C
a
t
"
??
0.9
]
blue\_box=[x3,\ \ y3,\ \ x4,\ \ y4,\ \ "Cat"\ \ 0.85] \\yellow\_box=[x5,\ \ y5,\ \ x6,\ \ y6,\ \ "Cat"\ \ 0.75] \\green\_box=[x1,\ \ y1,\ \ x2,\ \ y2,\ \ "Cat"\ \ 0.9]
blue_box=[x3,??y3,??x4,??y4,??"Cat"??0.85]yellow_box=[x5,??y5,??x6,??y6,??"Cat"??0.75]green_box=[x1,??y1,??x2,??y2,??"Cat"??0.9]
2、根据置信度过滤候选框
作为NMS中的第一步,我们按照置信度降序对框进行排序。排序后我们得到结果为:
b
b
o
x
_
l
i
s
t
=
[
g
r
e
e
n
_
b
o
x
,
b
l
u
e
_
b
o
x
,
y
e
l
l
o
w
_
b
o
x
]
bbox\_list=[green\_box,blue\_box,yellow\_box]
bbox_list=[green_box,blue_box,yellow_box] 然后我们定义一个置信度阈值。任何置信度低于此阈值的框都将被删除。对于本例,假设置信度阈值为0.8。使用该阈值,我们将删除黄色框,因为其置信度<0.8。这就给我们留下了:
b
b
o
x
_
l
i
s
t
=
[
g
r
e
e
n
_
b
o
x
,
b
l
u
e
_
b
o
x
]
bbox\_list=[green\_box,blue\_box]
bbox_list=[green_box,blue_box] 这一步操作后的结果图如下所示:
3、根据IOU过滤
由于框的置信度按降序排列,我们知道列表中的第一个框的置信度最高。我们从列表中删除第一个框,并将其添加到新列表中。在我们的例子中,我们将删除绿色框,并将其放入一个新列表中,比如bbox_list_new。
在这个阶段,我们为IOU定义了一个额外的阈值。此阈值用于删除具有高重叠度的框。其原因如下:如果两个框有大量重叠,并且它们也属于同一类,则很可能两个框都覆盖了同一对象(我们可以从上图验证这一点)。由于真实情况是每个对象只有一个框,因此我们尝试删除置信度较低的框。
在上述示例中,假设我们的IOU阈值为0.5
我们现在开始计算绿框的IOU,其中bbox_list中剩余的每个框也具有相同的类。在我们的例子中,我们将只使用蓝色框来计算绿色框的IOU。
如果绿框和蓝框的IOU大于我们定义的阈值0.5,我们将删除蓝框,因为它的置信度较低,并且有明显的重叠。
对图像中的每个框重复此过程,上述示例中最终只生成具有高置信度的唯一框。如下所示:
NMS算法
总结上述过程,我们可以得到NMS的计算过程如下:
- 定义置信度阈值和IOU阈值取值。
- 按置信度降序排列边界框bounding_box
- 从bbox_list中删除置信度小于阈值的预测框
- 循环遍历剩余框,首先挑选置信度最高的框作为候选框.
- 接着计算其他和候选框属于同一类的所有预测框和当前候选框的IOU。
- 如果上述任两个框的IOU的值大于IOU阈值,那么从box_list中移除置信度较低的预测框
- 重复此操作,直到遍历完列表中的所有预测框。
代码实现
def nms(boxes, conf_threshold = 0.7, iou_threshold = 0.4):
bbox_list_thresholded = []
bbox_list_new = []
boxes_sorted = sorted(boxes, reverse = True, key = lambda x: x[5])
for box in boxes_sorted:
if box[5] > conf_threshold:
bbox_list_thresholded.append(box)
else:
pass
while len(bbox_list_thresholded) > 0:
current_box = bbox_list_thresholded.pop(0)
bbox_list_new.append(current_box)
for box in bbox_list_thresholded:
if current_box[4] == box[4]:
iou = IOU(current_box[:4], box[:4])
if iou > iou_threshold:
bbox_list_thresholded.remove(box)
return bbox_list_new
相关解释如下:
def nms(boxes, conf_threshold=0.7, iou_threshold=0.4):
此函数将图像候选框列表、置信阈值和iou阈值作为输入。(这里将相应的默认值分别设置为0.7和0.4)
bbox_list_thresholded = []
bbox_list_new = []
接着我们创建了两个名为bbox_list_threshold和bbox_list_new的列表。
- bbox_list_threshold:包含筛选低置信度框后的新框列表
- bbox_list_new:包含执行NMS后的最终框列表
boxes_sorted = sorted(boxes, reverse=True, key = lambda x : x[5])
在上述术语定义中,按照置信度的降序对框列表进行排序,并将新列表存储在变量boxes_sorted中.
这里我们采用python的内置sorted函数对其进行排序,该函数根据key字段指定排序规则.
在我们的例子中,我们指定一个关键字reverse=True来按降序对列表进行排序,同时指定第二个关键字用于排序的约束。这里我们使用的lambda函数提供了一个映射,返回每个边界框的第5个元素(置信度)。
经过上述两个参数的设定,在遍历每个框时,排序函数将按照置信度对候选框按照降序排序。
for box in boxes_sorted:
if box[5] > conf_threshold:
bbox_list_thresholded.append(box)
else:
pass
我们遍历所有已排序的框,并移除置信度低于我们设置的阈值(conf_threshold=0.7)的框
while len(bbox_list_thresholded) > 0:
current_box = bbox_list_thresholded.pop(0)
bbox_list_new.append(current_box)
在上述根据置信度过滤候选框中,我们逐个循环遍历阈值框列表(bbox_list_threshold)中的所有框,直到列表清空。
我们首先从这个列表中删除(弹出)第一个框(当前框),因为它具有最高的可信度,然后将它附加到我们的最终列表中(bbox_list_new)。
for box in bbox_list_thresholded:
if current_box[4] == box[4]:
iou = IOU(current_box[:4], box[:4])
if iou > iou_threshold:
bbox_list_thresholded.remove(box)
然后,我们迭代列表bbox_list_threshold中所有剩余的框,并检查它们是否与当前框类别相同。(box[4]对应于类别)
如果两个框属于同一类,我们计算这些框之间的IOU, 如果IOU>IOU_threshold,我们将从列表bbox_list_thresholded中移除置信度较低的框。
return bbox_list_new
在非最大移植之后,我们返回更新后的框的列表bbox_list_new。
参考文章
|