一、规划模块核心概念:路径规划与轨迹规划的区别、全局规划与局部规划的关系、规划问题的数学建模

各位同学好,我是你们的老朋友。今天咱们正式进入规划模块的核心地带。说实话,很多新手一上来就被「路径规划」和「轨迹规划」这两个词搞晕了。我当年刚入行时也踩过这个坑——以为它们是一回事,结果在实车调试时出了大问题。

好,咱们一个一个来拆解。

1.1 路径规划 vs 轨迹规划:到底差在哪?

先问大家一个问题:你开车从北京到上海,是只需要知道「走哪条路」,还是需要知道「每个时刻踩多少油门、打多少方向盘」?

答案显然是后者。这就是路径规划和轨迹规划的本质区别。

  • 路径规划:只关心「空间上的几何路径」。它输出一条由点组成的折线或曲线,告诉你「从A到B,经过哪些位置」。它不关心时间,不关心速度。
  • 轨迹规划:在路径的基础上,加上「时间维度」。它告诉你「在什么时刻,到达哪个位置,以什么速度、什么加速度」。说白了,轨迹 = 路径 + 时间 + 运动状态。

一句话总结:路径规划回答「走哪条路」,轨迹规划回答「怎么走这条路」。

我在项目中遇到过这样一个案例:有一次我们用A*算法规划出一条很漂亮的路径,结果车一开上去就疯狂抖动。为什么?因为路径上有个急弯,但轨迹规划没有给这个弯道分配足够低的通过速度。嗯,这就是典型的「路径没问题,轨迹出问题」。

1.1.1 路径规划的输出

路径规划的输出通常是一个点序列:

// 路径规划输出示例
PathPoint {
  x: 10.5,  y: 20.3,  z: 0.0
  x: 11.2,  y: 21.0,  z: 0.0
  x: 12.0,  y: 21.8,  z: 0.0
  // ... 只有位置信息
}

你看,没有速度、没有时间戳。这就是路径。

1.1.2 轨迹规划的输出

轨迹规划的输出则丰富得多:

// 轨迹规划输出示例
TrajectoryPoint {
  x: 10.5,  y: 20.3,  z: 0.0,  t: 0.0,   v: 0.0,  a: 0.0
  x: 11.2,  y: 21.0,  z: 0.0,  t: 0.5,   v: 1.4,  a: 2.8
  x: 12.0,  y: 21.8,  z: 0.0,  t: 1.0,   v: 2.8,  a: 2.8
  // 位置 + 时间 + 速度 + 加速度
}

每个点都绑定了时间戳、速度、加速度。控制模块拿到这个,才知道「什么时候该加速,什么时候该刹车」。

我的调试习惯:在Autoware中,我经常先单独看路径规划的输出(用Rviz显示Path),确认几何路径没问题后,再打开轨迹(Trajectory)看速度曲线。如果车在某个点突然急刹,十有八九是轨迹规划的速度分配出了问题。

1.2 全局规划与局部规划:谁听谁的?

你想想看,一个自动驾驶系统要处理两种场景:

  • 从北京开到上海,需要知道走哪条高速、在哪个出口下——这是全局规划。
  • 前面突然有辆车加塞,需要紧急避让——这是局部规划。

全局规划和局部规划的关系,说白了就是「战略」和「战术」的关系。

维度 全局规划 局部规划
规划范围 起点到终点(公里级) 当前到前方几十米(米级)
更新频率 低(秒级甚至分钟级) 高(10Hz以上)
输入信息 高精地图、全局路线 激光雷达、摄像头、障碍物信息
输出 参考路径(Reference Path) 可执行轨迹(Trajectory)
典型算法 A*、Dijkstra、Lanelet2路由 MPC、DWA、TEB、Frenet优化

它们的关系是这样的:全局规划给出一条「参考线」,局部规划在这条参考线附近做微调。如果局部规划发现前方有障碍物,它会临时偏离参考线,绕过去之后再回到参考线上。

我曾经踩过的坑:有一次我把全局规划的更新频率设得太高(100ms一次),结果全局路径频繁变化,局部规划根本来不及收敛,车在路口来回摇摆。后来我改成2秒更新一次全局路径,局部规划只做局部优化,问题就解决了。记住:全局规划要「稳」,局部规划要「快」。

1.3 规划问题的数学建模

好,到了最硬核的部分。规划问题在数学上到底长什么样?

我个人习惯把规划问题抽象成三个要素:状态变量、约束条件、目标函数。

1.3.1 状态变量

在Autoware中,规划问题的状态变量通常包括:

  • 位置:\( (x, y, \theta) \) —— 横纵坐标和朝向角
  • 速度:\( v \) —— 纵向速度
  • 加速度:\( a \) —— 纵向加速度
  • 曲率:\( \kappa \) —— 路径的弯曲程度

有时候还会加上横摆角速度、前轮转角等,看具体场景。

1.3.2 约束条件

约束条件就是「不能做什么」。常见的约束有:

  • 运动学约束:车辆不能横着走,转弯半径有限。比如阿克曼转向模型要求 \( \dot{\theta} = v \cdot \tan(\delta) / L \)。
  • 动力学约束:加速度不能太大,否则乘客会晕车。一般 \( |a| \leq 3 \, m/s^2 \)。
  • 障碍物约束:车辆不能和障碍物碰撞。通常用「车辆多边形」和「障碍物多边形」的距离来判断。
  • 道路边界约束:车辆不能开出车道。这个在高精地图里用车道边界线来定义。

1.3.3 目标函数

目标函数就是「我们希望达到什么效果」。常见的优化目标:

  • 最小化行驶时间:尽快到达目的地
  • 最小化能量消耗:省电/省油
  • 最大化舒适性:减少急加速、急刹车
  • 最小化偏离参考线:尽量沿着全局路径走

把这些组合起来,一个典型的规划问题可以写成:

minimize:  w1 * (行驶时间) + w2 * (加速度变化率) + w3 * (偏离参考线距离)

subject to:
  车辆运动学方程
  加速度上下限
  障碍物距离 ≥ 安全阈值
  车道边界约束
  初始状态 = 当前车辆状态

其中 \( w1, w2, w3 \) 是权重系数。调这些权重,就是调车的「性格」——想要激进一点,就把时间权重调大;想要舒适一点,就把加速度变化率权重调大。

我的经验:在Autoware中调试MPC(模型预测控制)时,我最常调的就是这三个权重。有一次客户抱怨车「太肉」,起步慢。我把时间权重从0.1调到0.3,加速度变化率权重从0.5降到0.2,车立马就「精神」了。当然,代价是舒适性下降了一点点——这就是权衡。

1.4 知识体系总览

为了让大家更直观地理解这些概念之间的关系,我画了一张图:

规划模块核心概念关系图 全局规划 输入:高精地图 + 起点终点 输出:参考路径(Reference Path) 算法:A* / Dijkstra / Lanelet2 局部规划 输入:参考路径 + 传感器数据 输出:可执行轨迹(Trajectory) 算法:MPC / DWA / TEB 提供参考线 路径规划 只关心空间几何路径 输出:Path(无时间/速度) 轨迹规划 关心时间 + 速度 + 加速度 输出:Trajectory(含时间戳) 加入时间维度 规划问题的数学建模 状态变量 + 约束条件 + 目标函数 → 优化求解 全局规划 局部规划

这张图把今天讲的内容串起来了。你从上往下看:全局规划给局部规划提供参考线,路径规划是轨迹规划的基础(加入时间维度后变成轨迹),而所有规划问题最终都可以归结为一个数学优化问题。

核心要点回顾:

  • 路径规划 = 空间几何路径,轨迹规划 = 路径 + 时间 + 运动状态
  • 全局规划负责「战略」,局部规划负责「战术」,两者配合使用
  • 规划问题的数学本质:在约束条件下,优化目标函数
  • 权重系数决定车辆「性格」——激进还是舒适,全靠调参

好了,这一章的内容就到这里。记住这些核心概念,后面咱们讲具体算法时,你会发现自己理解起来快得多。下一章我们聊聊Autoware中规划模块的整体架构和数据流,到时候见。

可可精品资料库