持续创造,加快成长!这是我参加「日新计划 10 月更文应战」的第17天,点击查看活动概况

导读

这是一个十分简单通用的pipeline,很有参考价值。

使用OpenCV来实现自动驾驶中的车道线检测

在这个项目中,我运用Python和OpenCV构建了一个pipeline来检测车道线。该pipeline包括以下进程:

  • 相机校对
  • 视角转换
  • 色彩阈值和区域掩码
  • 寻找车道像素
  • 丈量车道曲线和曲率
  • 在原图画上显现成果

1. 相机校对

当相机在实际世界中看到3D方针并将其转换为2D图画时,就会发生图画失真,这种转换并不完美。畸变实际上改变了这些3D物体的形状和巨细。所以,分析相机图画的第一步,就是消除这种失真,这样你就能从中得到有用的信息。

使用OpenCV来实现自动驾驶中的车道线检测

有两种类型的畸变咱们感兴趣:径向畸变切向畸变

为了校准相机,咱们能够拍照已知形状的相片并校对失真误差。这个使命最常见的拍照对象是棋盘,由于它具有高对比度图画。

首要,咱们需要运用咱们的相机来拍照很多的棋盘图画,并检测这些图画中的一切角点。这能够运用OpenCV的cv2.findChessboardCorners()函数来完结。

使用OpenCV来实现自动驾驶中的车道线检测

cv2.findChessboardCorners()的成果

在这之后,咱们运用cv2.calibrateCamera()来核算畸变系数。径向畸变有3个系数:k1,k2,k3,切向畸变有2个系数:p1,p2。畸变点坐标核算公式如下,其间r为未畸变图画中某一点到图画畸变中心的已知间隔,畸变中心通常是该图画的中心(x_c, y_c)

使用OpenCV来实现自动驾驶中的车道线检测

径向畸变公式

使用OpenCV来实现自动驾驶中的车道线检测

切向畸变公式

使用OpenCV来实现自动驾驶中的车道线检测

使用OpenCV来实现自动驾驶中的车道线检测

畸变校对之后的成果

2. 透视改换

在这一步,咱们将图画转换为鸟瞰图。它将使今后的进程,如丈量车道曲率更简单。要改换图画,咱们首要需要从源图画上和方针图画上别离得到4个点,并运用函数cv2.getPerspectiveTransform()。当咱们想通过cv2.warpPerspective()函数改换图画时,该函数核算一个出一个3×3的改换矩阵

使用OpenCV来实现自动驾驶中的车道线检测

透视改换之前和之后的图画

3. 色彩阈值和区域掩码

使用OpenCV来实现自动驾驶中的车道线检测

HSV 和 HLS 色彩空间

HLS(色彩,亮度,饱和度)是RGB模型的一种替代表明。HLS是圆柱形几何图形,具有色相,角度维度,是实际的色彩。亮度表明色彩中混合了多少白色(或黑色)的色彩,饱和度表明色彩中有多少灰色。饱和度值为0,表明大部分都是灰色。

车道线的色彩为白色和黄色,两者都有一定范围内的饱和度值。因而,我只选择饱和度值在该范围内的像素。此外,利用亮度通道过滤掉一切亮度值较小的像素,能够检测出白色。

使用OpenCV来实现自动驾驶中的车道线检测

Hue, 亮度和饱和度值

区域掩码是去除图画中不太或许包括线的部分的进程。咱们能够看到,车道线主要出现在图片的下半部,因而,能够将图画的上半部分像素屏蔽以添加咱们的准确性,由于图画现在只包括那些更加或许是车道线的部分。

4. 找车道线像素

下一步,咱们需要分类哪些像素在左车道,右车道,或两者都不在。在此之后,咱们将找到能够最好拟合一切左车道像素的多项式方程,以及另一个最好拟合一切右车道像素的方程。

首要,我在图画下半部分的一切列上对像素值做统计得到直方图。在咱们的阈值二值化图画中,像素要么为0,要么为1,因而直方图中最杰出的两个峰值能够很好地指示车道线基线的x位置。

使用OpenCV来实现自动驾驶中的车道线检测

咱们能够用它作为搜索直线的起点。在这一点上,咱们能够运用一个在图画中向上移动的滑动窗口(沿着路进一步移动)来确定车道线的去向。

使用OpenCV来实现自动驾驶中的车道线检测

运用滑动窗口检测车道线像素

5. 找到车道线曲线并度量弯曲度

咱们现已估量了哪些像素属于左车道线和右车道线(别离用蓝色和赤色表明),并对这些像素位置拟合了一个多项式。咱们能够用这个多项式来核算车道曲率的半径以及车辆间隔车道中心的间隔。

回想一下,咱们现已找到了车道线的方程:

使用OpenCV来实现自动驾驶中的车道线检测

这是关于y的函数,而不是x的原因是,改换后图画中的车道线挨近笔直,并且对于多个y值或许具有相同的x值。

这儿的单位xy是以像素为单位的,但是咱们想将其转换为米来核算车辆的车道曲率和位置。假定2条线之间的间隔在像素坐标中是700像素。在实际生活中,这个间隔大约是3.7米。因而,水平方向上的每个像素相当于实际生活中的3.7/700米。咱们设这个值为mx = 3.7/700。在笔直方向上做同样的操作,咱们得到my = 30/720,表明每720个像素对应笔直方向上的30米。转能够这样做:

使用OpenCV来实现自动驾驶中的车道线检测

从像素坐标到真实世界坐标的转换

函数x=f(y)在任意点x处的曲率的半径为:

使用OpenCV来实现自动驾驶中的车道线检测

这很简单核算由于咱们只需要核算函数的一阶和二阶导数。

使用OpenCV来实现自动驾驶中的车道线检测

接下来,咱们想要核算咱们的汽车到车道中心的间隔。这能够通过核算车道中心和图画中心之间的水平间隔(以像素为单位)来完成。在这之后,咱们能够乘以常数mx来转换为真实的间隔。

6. 把成果显现回原图画

最终一步是将前一步的成果与原始图画结合起来。

为此,咱们需要还原之前转换的透视图,并将输出图画放到原始图画之上。

使用OpenCV来实现自动驾驶中的车道线检测

原图 vs 输出图

总结

这种特殊的pipeline在正常和模糊的情况下工作得很好,在这些情况下车道线更难检测。但是,由于这个pipeline 的参数数量有限,因而在雨雪等极点条件下,它的稳定性不够好。

总而言之,只需将几个算法放在一起,咱们就能够创立一个检测车道线的pipeline。首要,咱们校对相机失真。然后,咱们将其转换为鸟瞰图,过滤掉图画中不相关的部分,并运用“滑动窗口”找到车道像素。“最终,咱们核算了车道的方程,并丈量了车道曲率。

代码:github.com/Dt-Pham/Adv…

英文原文:medium.com/@dt99.pham/…