摘要
车道标记检测是自动驾驶和驾驶员辅助系统的重要组成部分。基于行的车道表示的现代深车道检测方法在车道检测基准上表现出良好的性能。通过初步的预测实验,我们首先解开了车道表示成分,以确定我们的方法的方向。我们发现,正确的车道位置已经是现有基于行的检测器的预测之一,并且准确表示交叉熵(IoU)
与地面实况的一致性分数是最有益的。基于这一发现,我们提出了与指标更好地相关的 LaneIoU
,将局部车道角度考虑在内。我们开发了一种名为CLRerNet
的新型检测器,该检测器具有LaneIoU
,用于目标分配成本和损失函数,旨在提高置信度分数的质量。通过包括交叉验证在内的仔细和公平的基准测试,我们证明了CLRerNet
的性能大大优于最先进的技术–在CULane
上,F1
得分为81.43%
,而现有方法为80.47%
,在CurveLanes
上为86.47%
,之前最好为86.10%
。代码地址 。
3.方法
3.1 网络设计和损失
基于行的表示形式利用了第 2 节中描述的四种类型中最准确但最简单的检测管道。从基于行的方法中,我们使用性能最好的CLRNet
[28]作为基线。网络原理图如图2所示。骨干网络(如ResNet
[9]和DLA
[26])和上采样网络提取的多层特征图,其空间维度为输入图像的(1/8、1/16、1/36)
。初始锚点由
N
a
N_a
Na可学习的锚点参数
(
x
a
,
y
a
,
θ
a
)
(x_a, y_a, θ_a)
(xa,ya,θa)组成,其中
(
x
a
,
y
a
)
(x_a, y_a)
(xa,ya)是起点,
θ
a
θ_a
θa是锚点的倾斜度。特征图沿着每个特征图进行采样,并输入到卷积和全连接(FC
)层。FC
层输出分类对数
c
c
c、锚点细化
δ
x
a
δx_a
δxa、
δ
y
a
δy_a
δya、
δ
θ
a
δθ_a
δθa、长度
l
l
l 和局部
x
x
x 坐标细化
δ
x
δx
δx 张量。通过
δ
x
a
δx_a
δxa、
δ
y
a
δy_a
δya和
δ
θ
a
δθ_a
δθa细化的锚点对更高分辨率的特征图进行重采样,并重复该过程三次。池化的特征通过交叉注意力与特征图进行交互,并在不同的细化阶段进行连接。车道预测表示为分类(置信度)的logits
和一组
x
x
x坐标
N
r
o
w
N_{row}
Nrow,从最终的
x
a
x_a
xa、
y
a
y_a
ya、
θ
a
θ_a
θa、
l
l
l和
δ
x
δx
δx计算出来。关于细化机制的更多细节可以在[28]中找到。在训练过程中,接近GT的预测是通过动态分配器[5]分配的。分配的预测将回归到相应的 GT,并学习被归类为正数。
L
=
λ
0
L
reg
+
λ
1
L
cls
+
λ
2
L
seg
+
λ
3
L
LaneIoU
L=\lambda_{0} L_{\text {reg }}+\lambda_{1} L_{\text {cls }}+\lambda_{2} L_{\text {seg }}+\lambda_{3} L_{\text {LaneIoU }}
L=λ0Lreg +λ1Lcls +λ2Lseg +λ3LLaneIoU
其中
L
reg
L_{\text {reg }}
Lreg 是
smooth-L1
\text {smooth-L1}
smooth-L1损失来回归锚定参数
(
x
a
,
y
a
,
θ
a
)
\left(x_{a}, y_{a}, \theta_{a}\right)
(xa,ya,θa)和
l
l
l,
L
cls
L_{\text {cls }}
Lcls 是 focal loss
用于正的或负的锚定分类,
L
reg
L_{\text {reg }}
Lreg 每像素分割掩模的辅助交叉熵损失,
L
LaneIoU
L_{\text {LaneIoU }}
LLaneIoU 新引入的LaneIoU
损失。
3.2 Oracle实验
我们进行了初步的oracle实验,以确定我们的方法的方向。部分将训练基线模型中的预测组件替换为 GT,以分析每个车道表示组件的改进空间。oracle实验结果如表1所示。基线模型(第一行)是在没有冗余帧的情况下训练的 CLRNet-DLA34。置信度阈值设置为 0.39,这是通过交叉验证获得的(参见第 4.1 和 4.2 小节)。
接下来,我们计算预测和GTs之间的度量IoU作为oracle置信度分数。对于每个预测,使用gt中的最大IoU作为oracle评分。在这种情况下,预测的车道坐标不会改变。F150跳转到98.47,接近完美的分数(第二排)。结果表明,正确的车道已经在预测中,但置信分数需要准确地预测代表度量IoU。
其他组件是锚参数 -
x
a
x_a
xa、
y
a
y_a
ya、
θ
a
θ_a
θa 和长度
l
l
l,用于确定车道坐标。我们用GT的参数和车道长度来改变锚参数和车道长度(分别为第三排和第四排)。尽管逐行细化
δ
x
δ_x
δx 没有改变,但预言机锚点参数将
F
1
50
F1_{50}
F150 提高了 9 个点。另一方面,预言机长度不会显着影响性能。结果得出了第二个建议,即锚参数(
x
a
x_a
xa、
y
a
y_a
ya、
θ
a
θ_a
θa)在车道定位方面很重要。
我们关注第一个发现,目的是通过改进车道相似度函数来学习高质量的置信分数。
3.3 LaneIoU
现有的方法[15]和[28]分别利用水平距离和水平
IoU
\text{IoU}
IoU作为相似度函数。然而,这些定义与使用分割掩模计算的指标
IoU
\text{IoU}
IoU不匹配。例如,当车道倾斜时,
metric-IoU
\text{metric-IoU}
metric-IoU对应的水平距离大于垂直车道的水平距离[虚线框内]。为了弥合差距,我们引入了一种可微分的局部角度感知
IoU
\text{IoU}
IoU 定义,即
LaneIoU
\text{LaneIoU}
LaneIoU。图 3 显示了两条倾斜曲线之间的
IoU
\text{IoU}
IoU计算示例。我们在同一车道实例对上比较了
LineIoU
\text{LineIoU}
LineIoU [28]和
LaneIoU
\text{LaneIoU}
LaneIoU。
LineIoU
\text{LineIoU}
LineIoU应用了一个恒定的虚拟宽度,而不管车道的角度如何,而虚拟车道在倾斜的部分变得“很薄”[如图3,车道弯曲部分,红线对比]。在我们的
LaneIoU
\text{LaneIoU}
LaneIoU,交集和并集的计算考虑了每个车道局部部分的倾斜度[弯车道部位,宽度不变或损失很小]。我们将
Ω
p
q
\Omega_{pq}
Ωpq定义为
p
p
p 和
q
q
q两个车道都存在的
y
y
y切片集,以及只有一个车道存在的
Ω
p
\Omega_p
Ωp或
Ω
q
\Omega_q
Ωq。
LaneIoU
\text{LaneIoU}
LaneIoU计算如下:
LaneIoU
=
∑
i
=
0
H
I
i
∑
i
=
0
H
U
i
\text { LaneIoU }=\frac{\sum_{i=0}^{H} I_{i}}{\sum_{i=0}^{H} U_{i}}
LaneIoU =∑i=0HUi∑i=0HIi
I
i
I_{i}
Ii和
U
i
U_{i}
Ui定义:
I
i
=
min
(
x
i
p
+
w
i
p
,
x
i
q
+
w
i
q
)
−
max
(
x
i
p
−
w
i
p
,
x
i
q
−
w
i
q
)
U
i
=
max
(
x
i
p
+
w
i
p
,
x
i
q
+
w
i
q
)
−
min
(
x
i
p
−
w
i
p
,
x
i
q
−
w
i
q
)
\begin{array}{l} I_{i}=\min \left(x_{i}^{p}+w_{i}^{p}, x_{i}^{q}+w_{i}^{q}\right)-\max \left(x_{i}^{p}-w_{i}^{p}, x_{i}^{q}-w_{i}^{q}\right) \\ U_{i}=\max \left(x_{i}^{p}+w_{i}^{p}, x_{i}^{q}+w_{i}^{q}\right)-\min \left(x_{i}^{p}-w_{i}^{p}, x_{i}^{q}-w_{i}^{q}\right) \end{array}
Ii=min(xip+wip,xiq+wiq)−max(xip−wip,xiq−wiq)Ui=max(xip+wip,xiq+wiq)−min(xip−wip,xiq−wiq)
这里
i
∈
Ω
p
q
i \in \Omega_{pq}
i∈Ωpq,当车道重叠时,车道的交叉点为正,否则为负。如果
i
∉
Ω
p
q
i \notin \Omega_{pq}
i∈/Ωpq,
I
i
I_{i}
Ii和
U
i
U_{i}
Ui的计算如下:
I
i
=
0
,
U
i
=
2
w
i
k
if
k
∈
{
p
,
q
}
,
i
∈
Ω
k
I
i
=
0
,
U
i
=
0
if
i
∉
(
Ω
p
q
∪
Ω
p
∪
Ω
q
)
\begin{array}{l} I_{i}=0, U_{i}=2 w_{i}^{k} \text { if } k \in\{p, q\}, i \in \Omega_{k} \\ I_{i}=0, U_{i}=0 \text { if } i \notin\left(\Omega_{p q} \cup \Omega_{p} \cup \Omega_{q}\right) \end{array}
Ii=0,Ui=2wik if k∈{p,q},i∈ΩkIi=0,Ui=0 if i∈/(Ωpq∪Ωp∪Ωq)
考虑局部角度,计算虚拟车道宽度
w
p
i
w_p^i
wpi和
w
q
i
w_q^i
wqi:
w
i
k
=
w
lane
2
(
Δ
x
i
k
)
2
+
(
Δ
y
i
k
)
2
Δ
y
i
k
w_{i}^{k}=\frac{w_{\text {lane }}}{2} \frac{\sqrt{\left(\Delta x_{i}^{k}\right)^{2}+\left(\Delta y_{i}^{k}\right)^{2}}}{\Delta y_{i}^{k}}
wik=2wlane Δyik(Δxik)2+(Δyik)2
其中,
k
∈
{
p
,
q
}
k \in \{p,q\}
k∈{p,q}和
Δ
x
i
\Delta x_i
Δxi和
Δ
y
i
\Delta y_i
Δyi表示车道点坐标的局部变化。公式7补偿了车道的倾斜变化,表示了一般的行向车道IoU计算。当车道是垂直时,此时
Δ
x
i
→
0
\Delta x_i \rightarrow 0
Δxi→0,
w
i
w_i
wi等于
w
l
a
n
e
/
2
w_{lane}/2
wlane/2,并随着车道的倾斜而变大。
w
l
a
n
e
w_{lane}
wlane是控制
IoU
\text {IoU}
IoU计算严格程度的参数。
CULane metric
\text {CULane metric }
CULane metric 使用 30 像素来表示 (590,1640) 的分辨率。代码如下:
def _calc_lane_width(self, pred, target):
"""
Calculate the LaneIoU value between predictions and targets
Args:
pred: lane predictions, shape: (Nl, Nr), relative coordinate.
target: ground truth, shape: (Nl, Nr), relative coordinate.
Returns:
torch.Tensor: virtual lane half-widths for prediction at pre-defined rows, shape (Nl, Nr).
torch.Tensor: virtual lane half-widths for GT at pre-defined rows, shape (Nl, Nr).
Nl: number of lanes, Nr: number of rows.
"""
n_strips = pred.shape[1] - 1
dy = self.img_h / n_strips * 2 # two horizontal grids
_pred = pred.clone().detach()
pred_dx = (_pred[:, 2:] - _pred[:, :-2]) * self.img_w # pred x difference across two horizontal grids
pred_width = self.lane_width * torch.sqrt(pred_dx.pow(2) + dy**2) / dy
pred_width = torch.cat([pred_width[:, 0:1], pred_width, pred_width[:, -1:]], dim=1)
target_dx = (target[:, 2:] - target[:, :-2]) * self.img_w
target_dx[torch.abs(target_dx) > self.max_dx] = 0
target_width = self.lane_width * torch.sqrt(target_dx.pow(2) + dy**2) / dy
target_width = torch.cat([target_width[:, 0:1], target_width, target_width[:, -1:]], dim=1)
return pred_width, target_width
计算交集和并集
def _calc_over_union(self, pred, target, pred_width, target_width):
"""
Calculate the line iou value between predictions and targets
Args:
pred: lane predictions, shape: (Nlp, Nr), relative coordinate
target: ground truth, shape: (Nlt, Nr), relative coordinate
pred_width (torch.Tensor): virtual lane half-widths for prediction at pre-defined rows, shape (Nl, Nr).
target_width (torch.Tensor): virtual lane half-widths for GT at pre-defined rows, shape (Nl, Nr).
Returns:
torch.Tensor: calculated overlap, shape (Nlp, Nlt, Nr).
torch.Tensor: calculated union, shape (Nlp, Nlt, Nr).
Nlp, Nlt: number of prediction and target lanes, Nr: number of rows.
"""
px1 = pred - pred_width
px2 = pred + pred_width
tx1 = target - target_width
tx2 = target + target_width
ovr = torch.min(px2[:, None, :], tx2[None, ...]) - torch.max(
px1[:, None, :], tx1[None, ...])
union = torch.max(px2[:, None, :], tx2[None, ...]) - torch.min(
px1[:, None, :], tx1[None, ...])
return ovr, union
计算 LaneIoU \text {LaneIoU} LaneIoU
def __call__(self, pred, target, start=None, end=None):
"""
Calculate the line iou value between predictions and targets
Args:
pred: lane predictions, shape: (Nlp, Nr), relative coordinate. 192x72
target: ground truth, shape: (Nlt, Nr), relative coordinate. 3x72
Returns:
torch.Tensor: calculated IoU matrix, shape (Nlp, Nlt)
Nlp, Nlt: number of prediction and target lanes, Nr: number of rows.
"""
pred_width, target_width = self._calc_lane_width(pred, target)
ovr, union = self._calc_over_union(pred, target, pred_width, target_width) # shape 192x3x72
if self.use_pred_start_end is True:
ovr, union = self._set_invalid_with_start_end(pred, target, ovr, union, start, end, pred_width, target_width)
else:
ovr, union = self._set_invalid_without_start_end(pred, target, ovr, union)
iou = ovr.sum(dim=-1) / (union.sum(dim=-1) + 1e-9) # shape 192x3
return iou * self.weight
在图4中,通过计算与
CULane metric
\text {CULane metric }
CULane metric 的相关性来比较
LineIoU
\text {LineIoU}
LineIoU [28]与我们的
LaneIoU
\text {LaneIoU}
LaneIoU。我们用
LineIoU
\text {LineIoU}
LineIoU或
LaneIoU
\text {LaneIoU}
LaneIoU值替换每个预测的置信度得分,并计算
metric IoU
\text {metric IoU}
metric IoU。每个预测都选择
IoU
\text {IoU}
IoU最大的
GT
\text {GT}
GT。显然,我们的
LaneIoU
\text {LaneIoU}
LaneIoU比
metric IoU
\text {metric IoU}
metric IoU的相关性更好,这主要是由于消除了车道角度的影响。
3.4 样品分配
如果在训练中锚被分配为正的,那么信心分数就会很高。我们采用LaneIoU进行样本分配,使检测器的置信度分数接近于基于分割的IoU。[28]使用SimOTA分配器[5]为每个GT车道ti动态分配ki锚点。锚的数量ki是通过计算所有锚的正iou的总和来确定的。我们使用LaneIoU作为:
k
i
=
∑
j
=
1
m
L
a
n
e
I
o
U
(
p
j
,
t
i
)
k_{i}=\sum_{j=1}^{m}L a n eIo U(p_{j},t_{i})
ki=j=1∑mLaneIoU(pj,ti)
这里
m
m
m是锚点数量,
i
=
0
,
1
,
.
.
.
.
n
i\ =\ 0,1,....n
i = 0,1,....n是
n
n
n个GT车道的索引。
p
j
p_j
pj是预测的道路,
j
=
0
,
1
,
.
.
.
.
m
j\ =\ 0,1,....m
j = 0,1,....m是
m
m
m个预测的索引。
k
i
k_i
ki是1到
k
m
a
x
k_{max}
kmax的一段。混淆矩阵决定了每个GT的分配的优先级。在目标检测中,[5]采用边界盒IoU和分类成本之和。在车道检测中,CLRNet [28]利用了分类成本和包括水平距离、角度差和起点距离在内的车道相似度成本。然而,直接表示评估指标的成本对于确定预测的优先级更为简单。我们将成本矩阵定义为:
c
o
s
t
j
i
=
−
L
a
n
e
I
o
U
n
o
r
m
(
p
j
,
t
i
)
+
λ
f
c
l
a
s
s
(
p
j
,
t
i
)
c o s t_{j i}=-L a n e{I o U_{n o r m}}(p_{j},t_{i})+\lambda f_{c l a s s}(p_{j},t_{i})
costji=−LaneIoUnorm(pj,ti)+λfclass(pj,ti)
其中,
λ
\lambda
λ是平衡这两个成本的参数,而
f
c
l
a
s
s
f_{c l a s s}
fclass是用于分类的成本函数,如focal loss
[14]。LaneIoU从其最小值到最大值被归一化。提出的公式(eq。8和9)实现适当数量的锚点的动态样本分配,并根据评估指标进行优先排序。综上所述,与CLRNet相比,我们的CLRerNet引入了LaneIoU作为动态k分配函数、分配成本函数和损失函数,以学习与度量IoU更好相关的高质量证据分数。