在上一讲《Coursera自动驾驶课程第11讲:2D Object Detection》我们学习了深度学习的一个重要应用:目标检测
。
本讲我们将学习深度学习的另一个重要应用:语义分割
。这是图片像素级的一个重要应用。
B站视频链接:https://www.bilibili.com/video/BV1PE411D72p。
文章目录
- 1. The Semantic Segmentation Problem
- 1.1 Overview
- 1.2 Mathematical Problem Formulation
- 1.3 Evaluation Metrics
- 2. ConvNets for Semantic Segmentation
- 2.1 Review
- 2.2 Upsampling Layer
- 2.3 Feature Decoder
- 3. Semantic Segmentation for Road Scene Understanding
- 3.1 3D Drivable Surface Estimation
- 3.2 Semantic Lane Estimation
1. The Semantic Segmentation Problem
1.1 Overview
让我们从定义语义分割问题开始:给定输入图像,我们要对每个像素进行分类
。类别可以是静态道路元素
,例如道路,人行道,立杆,交通信号灯和交通标志,也可以是动态运动目标
,例如汽车,行人和骑自行车的人。此外,我们始终有一个背景类
,其中包含我们未包含在预设类别中的任何类别。
1.2 Mathematical Problem Formulation
与目标检测一样,我们定义一个语义分割函数,输入是图像,函数参数为θ\thetaθ。
f(x;θ)=[Sclass 1,…,Sclass k]f(x ; \theta)=\left[S_{\text {class }_{1}}, \ldots, S_{\text {class }_{k}}\right]f(x;θ)=[Sclass 1,…,Sclass k]
那么,我们如何调整神经网络来进行分割呢? 给定图像,我们将每个像素作为输入,并输出每个像素的分类得分。
在下图中,道路像素的道路得分应该很高,而其他类别的得分要低得多。
尝试执行语义分割时,我们通常会遇到许多与目标检测相同的问题。例如,遮挡和截断
使得难以准确预测目标边界。缩放
也是一个主要问题,因为我们需要处理具有精细细节的近距离目标和仅由几个像素捕获的远距离目标。我们还需要能够处理场景中的光照变化。
造成这种困难的原因是图像空间中的边界不明确,尤其是对于诸如杆子之类的细小物体,诸如道路和人行道之类的外观相似的物体以及距离较远的物体。
1.3 Evaluation Metrics
现在让我们介绍一些评价指标。
- 第一个指标是
真阳性(TP)
:正确分类的像素数。 - 第二个指标是
假阳性(FP)
:即错误分类的像素数。 - 第三个指标是
假阴性(FN)
:即应进行分类但最终未分类的像素数。
使用以上三个评价指标,我们可以计算出最常用的语义分割评估度量,即IOUclassIOU_{class}IOUclass。 计算公式为:
IOUclass =TPTP+FP+FNI O U_{\text {class }}=\frac{T P}{T P+F P+F N}IOUclass =TP+FP+FNTP
让我们看一个直观示例。道路分割数据表示为每个像素对应一个类。类似地,通过将输出得分最高的类别作为我们的预测类别,将预测也以相似的格式进行。
现在,我们开始计算由RRR表示的道路类别
的IOU得分。第一个要度量的指标是TP=3TP=3TP=3。我们可以通过计算预测中正确分类的道路像素数。第二个指标FP=0FP=0FP=0;第三个指标FN=2FN=2FN=2。那么,我们最终的IOU得分为:
IOURoad =33+0+2=35I O U_{\text {Road }}=\frac{3}{3+0+2}=\frac{3}{5}IOURoad =3+0+23=53
同样地,辅路的IOU得分为:
IOURoad =44+2+0=46I O U_{\text {Road }}=\frac{4}{4+2+0}=\frac{4}{6}IOURoad =4+2+04=64
![]() | ![]() |
2. ConvNets for Semantic Segmentation
2.1 Review
在本小节,我们将学习如何使用卷积神经网络执行语义分割任务
。 使用置信度
进行语义分割比目标检测要容易一些。 与用于目标检测的卷积网络不同,对于语义分割,训练和推理阶段实际上是相同的
。 但是,也有一些需要我们注意的。
让我们先快速回顾一下语义分割问题。 语义分割输入为摄像机图像
,并为该图像中的每个像素进行类别判断。 我们将此问题建模为函数逼近问题。和目标检测一样, 我们可以使用哪种卷积网络来执行此函数逼近呢?
一种想法是使用与目标检测相同的网络模型。 也就是说,特征提取器后面是输出层
。 我们在这里不需要使用锚盒,因为我们没有尝试定位目标。 与用于目标检测的特征提取器一样,我们可以使用VGG网络。
让我们看看通过此特征提取器时输入图像的大小会如何变化? 与目标检测一样,在每个池化层之后,图像大小将减小一半。 另一方面,由于卷积层,特征深度将增加。 最终特征提取器的输出特征图将被下采样16倍。 我们可以根据需要添加任意数量的卷积池块,但这将进一步缩小我们的特征图。 但是,我们希望我们的输出对图像中的每个像素都有一个分类
。
那么,如果给定的下采样特征映射比原始输入小16倍,我们如何实现上述目标?
2.2 Upsampling Layer
一个简单的解决方案如下:
- 首先可以将16倍
下采样
的输出特征图通过softmax层来计算输出。 - 然后,通过获取softmax层获得的最高类别得分来确定子采样输出中每个像素的类别。
- 最后一步是
上采样
,将下采样后的输出恢复为原始图像大小。
现在让我们看一下上采样如何提高图像分辨率
。 我们想在2×22\times22×2的图像上使用近邻上采样
。 图像块的像素颜色代表每个像素的不同值。 我们进行上采样以使其原始大小增加一倍。 上采样后的填充图像颜色为近邻图像颜色。上采样引起的问题是上采样的输出图像具有非常粗糙的边界。因此,上采样乘数SSS为2。最终得到的输出维度大小为:
Wout =S×Win Hout =S×Hin Dout =Din W_{\text {out }}=S \times W_{\text {in }} \\H_{\text {out }}=S \times H_{\text {in }} \\D_{\text {out }}=D_{\text {in }}Wout =S×Win Hout =S×Hin Dout =Din
回顾一下,语义分割中最具挑战性的问题之一是在目标周围很难获得平滑的边界
,因为图像空间中的边界通常是模棱两可的,尤其是对于诸如水池之类的细小物体,诸如道路和人行道之类的外观相似的物体以及距离较远的物体而言。
原始的上采样还会引发另外一个问题。 宽度或高度小于16像素大小的目标通常会在其上采样图像中完全消失
。那么我们如何解决呢?
2.3 Feature Decoder
为了解决以上问题,研究人员为此提出了特征解码器
。 特征解码器可以被认为是特征提取器的镜像
。当我们通过特征解码器时,通常会提供所需的平滑边界。
现在,让我们分析一下特征图在通过特征解码器时尺寸如何变化。 提醒一下,输入特征图以512的深度下采样16倍。类似于特征提取器,每个上采样卷积块称为反卷积
。 当然,当前的研究人员之间就该术语是否准确存在争议。 但是我们将在这里使用它来指代卷积池的逆操作。 当我们经过第一个反卷积块时,我们的输入特征图被上采样到输入分辨率的2倍。 当我们继续进行解码器的其余部分时,最终会得到分辨率与输入图像相似大小的特征图
。为了降低计算复杂度,我们通常会缩小特征图的深度。但这是一个取决于具体的应用程序。请注意,在许多建议的语义分割方法中,这种上采样机制是最简单的。
现在,我们已经具有与输入图像相似大小的特征图,我们需要生成语义分割输出
。我们可以通过线性输出层执行语义分割,然后再执行softmax函数。该层与我们在目标检测中描述的分类输出层非常相似。实际上,该层为每个像素提供了一个kkk维矢量,其中第kkk个元素是神经网络对像素属于第kkk类的置信。
根据定义,语义分割问题要求神经网络为每个像素提供一个单独的类。 为了学习如何执行此任务,将交叉熵分类损失
再次用于训练神经网络。 这种损失类似于我们用于目标检测分类中的损失。 函数形式为:
Lcls=1Ntotal∑iCrossEntropy(si∗,si)L_{c l s}=\frac{1}{N_{t o t a l}} \sum_{i} \operatorname{CrossEntropy}\left(s_{i}^{*}, s_{i}\right)Lcls=Ntotal1i∑CrossEntropy(si∗,si)
总结一下:我们得出了以下用于语义分割的模型。特征提取器将图像作为输入,得到特征图;然后,解码器获取此特征图并对其进行上采样以获得与原始输入图像相似分辨率的特征图。最终,线性层后跟softmax函数,为输入图像中的每个像素生成分类向量。
3. Semantic Segmentation for Road Scene Understanding
3.1 3D Drivable Surface Estimation
现在,让我们使用语义分割为自动驾驶汽车执行一些有用的任务。我们将要讨论的第一个任务是从3D语义分割输出中可驾驶道路
。可驾驶空间定义为车辆前方安全驾驶的区域
。在语义分割的上下文中,可驾驶表面包括公路,人行横道,车道标记线,停车区域。估计可驾驶道路非常重要,因为它是从3D深度传感器构建占用栅格的主要步骤之一。
但是现在,让我们描述如何从语义分割输出中执行可驾驶的道路估计。
- 首先,我们使用ConvNet生成图像的语义分割输出。
- 然后将点云投影到图像平面来生成该帧中像素的3D坐标。通过传感器之间的已知外部标定,我们可以将激光雷达点投影到图像平面中,并将其与相应的像素匹配。
- 然后,我们继续选择属于可驾驶路面类别的3D点。
- 最后,我们使用3D点的此子集来估计可驾驶道路模型。
现在让我们描述在分割图像数据和激光雷达点的情况下,如何拟合可驾驶的曲面模型。
我们首先定义平面模型:
ax+by+z=da x+b y+z=dax+by+z=d
我们可以得到一个线性方程组,以使用该平面模型的参数作为度量来估计参数,每个点都被标识为属于可驾驶曲面上的点。
p=[a,b,d],argminA(Ap−B)p=[a, b, d], \quad \underset{A}{\operatorname{argmin}}(A p-B)p=[a,b,d],Aargmin(Ap−B)
A=[x1y1−1x2y2−1⋮⋮⋮xNyN−1],B=[−z1−z2⋮−zN]A=\left[\begin{array}{ccc}x_{1} & y_{1} & -1 \\ x_{2} & y_{2} & -1 \\ \vdots & \vdots & \vdots \\ x_{N} & y_{N} & -1\end{array}\right], \quad B=\left[\begin{array}{c}-z_{1} \\ -z_{2} \\ \vdots \\ -z_{N}\end{array}\right]A=⎣⎢⎢⎢⎡x1x2⋮xNy1y2⋮yN−1−1⋮−1⎦⎥⎥⎥⎤,B=⎣⎢⎢⎢⎡−z1−z2⋮−zN⎦⎥⎥⎥⎤
现在,向量ppp为模型参数,并且测量值为矩阵AAA和BBB。我们可以使用最小二乘法找到该线性方程组的解。 最终的结果为:
p=(ATA)−1ATBp=\left(A^{T} A\right)^{-1} A^{T} Bp=(ATA)−1ATB
该模型具有三个参数
,因此,至少需要三个非共线点才能求解
。这里我们我们使用RANSAC算法来拟合可驾驶曲面模型。
- 首先,我们随机选择适合模型的最小数据点。在这种情况下,我们随机选择3D中的三个点。
- 其次,我们使用这三个点来计算模型参数a,b,da,b,da,b,d,并使用
最小二乘法
求解平面参数。 - 然后,我们继续确定满足这些模型参数的3D点的数量。通常,对于可驾驶的曲面估计,大多数异常值是位于边界处的错误分割输出的结果。如果异常点数比较少,则终止并返回计算的平面参数。否则,我们将随机采样三个新点并重复该过程。如果道路实际上是平坦的,则使用平面模型非常有效,这在许多驾驶场景中都是有效的假设。对于更复杂的场景,例如从平坦的道路进入陡峭的高速公路入口,则需要更复杂的模型。
3.2 Semantic Lane Estimation
尽管我们估计了可驾驶的路面,但我们仍未确定允许汽车在该库面上行驶的位置。通常,车辆应行驶在车道内
,这取决于车道标记或道路边界。车道线估计是估计自动驾驶汽车在给定的可行驶路面下可以行驶的位置的任务。文献中存在许多方法可以完成此任务。例如,某些方法直接从ConvNets估计车道线标记,以确定汽车可以行驶到哪里。但是,对于更高级别的决策,无人驾驶汽车也应了解车道边界处的情况。
我们将估计车道及其边界处发生的事情称为语义车道估计
。注意,如果我们使用语义分割的输出来估计车道,我们将轻松获得边界分类。让我们通过一个简单的方法来解决这个问题,以弄清车道估计任务。
- 给定语义分割模型的输出,我们首先
提取属于作为车道分隔符的类的像素的掩码
。例如,此类可以包括路缘石,车道标记或栏杆。 - 然后,我们将边缘检测器应用于掩码。在这里,我们使用著名的边缘检测器canny边缘检测器。输出是分类为边缘的像素,将用于估计车道边界。
- 最后一步是确定要使用哪种模型来估算车道。为了检测输出边缘图中的线,我们需要对齐的检测器。
霍夫变换检测算法
被广泛使用,并且能够检测边缘图中的多条线。 - 可以根据当前情况应用进一步的优化。例如,我们知道如果摄像机朝向与运动方向一致,则车道不应为水平线。此外,我们可以删除任何不属于可驾驶曲面的线,以获得最终的车道边界元集。