1. 项目概述:为什么横向轨迹跟踪是自动驾驶绕不开的坎
做了几年车辆控制相关的仿真工作,我越来越觉得横向轨迹跟踪是底盘控制里最“磨人”的一个方向。它不像纵向控制那样只管跟车距、踩刹车,横向控制要在高速运动状态下,让车辆精确贴合期望路径,同时还得保证乘客坐着不难受、车辆在物理极限内不失控。这个“基于多算法的车辆横向轨迹跟踪 Carsim、Simulink 联合仿真”项目,本质上是把三种主流控制策略放到同一个平台上横向对比,用同一辆车、同一条路、同一个测试工况去考核它们的表现。项目里包含了完整的 Matlab 代码、Simulink 模型和 Carsim 车辆模型配置,能够完成从“期望轨迹生成 → 控制算法解算 → 车辆动力学响应 → 误差统计分析”的闭环仿真链路。
用大白话说,这个项目解决的是这样一个问题:给一辆车一个目标轨迹(比如一个双移线或者一个带曲率变化的弯道),你希望车自己沿着这条线走,那用什么算法控制方向盘最靠谱?是简单粗暴的纯跟踪,还是计算量稍大的线性二次型调节器 LQR,抑或是号称“带约束优化”的模型预测控制 MPC?这三种算法在这个项目里可以全部跑出来,直接对比横向误差、横摆角误差、控制量曲线和计算耗时,结论非常直观。
这个项目比较适合三类人:第一类是在校研究生,尤其是做车辆工程、控制工程课题的学生,拿这个做课程设计或者毕业论文的仿真支撑非常合适;第二类是刚入行底盘控制或者自动驾驶算法岗的工程师,用它来建立对整个横向控制链条的整体认知,比一上来就看论文用真车试要稳妥得多;第三类是自学做项目积累经验的开发者,整套代码和模型是完整可跑的,能省掉大量搭环境的痛苦。
我在实际跑这套东西的过程中踩了不少坑,也把很多“文档里不会写”的经验攒下来了。下面我从模型原理、算法选型、联合仿真配置、结果分析和常见问题几个维度逐层拆解,尽量把这个项目讲透。
2. 车辆横向动力学模型:所有控制算法的数学地基
2.1 为什么精度和实时性必须做权衡
横向控制算法跑的都是在“车辆模型”上做预测或者做状态反馈。这里的车辆模型不是越精确越好,因为模型越精细,参数越多、计算越慢,控制周期一被拉长,实时性就崩了。常见的方案是用一个简化却抓住了核心特征的“自行车模型”。它假设车辆左右两侧轮胎的动力学特性完全对称,于是把四个车轮等效成前轴一个轮、后轴一个轮,整车被简化成一个横向有侧偏、纵向有速度的刚体模型。这个模型忽略了悬架运动、载荷转移、轮胎的非线性大滑移等复杂因素,但足够描述车辆在中低速工况下的横摆和侧向运动特征,是工程上最常用的折中方案。
这里有一层更实际的逻辑:如果做联合仿真,控制算法里用的预测模型和 Carsim 里跑的高精度车辆模型是两套东西。Carsim 提供的是“真实车辆”的响应,控制算法内部是“简化模型”的近似。两套模型的差异本身就是控制算法的鲁棒性测试的一部分。模型匹配得好,控制效果好;模型差得多,也能看出来哪个算法更强壮。
2.2 自行车模型的核心数学公式拆解
自行车模型的推导过程在很多教材里都有,这里我直接给工程应用里最常用的形式。以车身坐标系为参考,车辆状态通常取为横向位置偏差、横摆角偏差和横摆角速度:
横向位置偏差变化率:
[ \dot{e_y} = v_x e_\psi ]
其中 (v_x) 是纵向车速,(e_\psi) 是横摆角偏差。这个式子说明横向偏差的变化由纵向速度和航向偏差共同决定,直观理解就是:车头方向偏了,车就会一边往前走一边越发偏离目标线。
横摆角偏差变化率:
[ \dot{e_\psi} = \gamma - v_x \kappa ]
其中 (\gamma) 是横摆角速度,(\kappa) 是参考轨迹的曲率。这个式子描述了车辆实际转动角速度与目标轨迹所需转动角速度之差。
横摆角速度动态:
[ \dot{\gamma} = \frac{2C_f + 2C_r}{I_z v_x} \text{(...)} + \frac{2C_f l_f - 2C_r l_r}{I_z v_x} \text{(...)} ]
完整公式写出来会比较长,核心逻辑是横摆角速度由前轮转角 (\delta) 和车辆横向速度共同决定,前轮侧偏刚度和后轮侧偏刚度系数在这里起着决定性作用。
前轮转角到横摆角速度的传递函数在工程上非常重要。它近似是一个二阶振荡环节,增益随车速增大而增大,阻尼随车速增大而减小。这解释了为什么高速工况下车辆横摆响应更灵敏、更容易失控,也是 LQR 和 MPC 在设计时都要考虑控制增益随车速变化的原因。
2.3 控制周期和模型精度对算法表现的影响
仿真步长一般设置成 1ms 到 10ms。Carsim 内部求解动力学方程用的是变步长积分,精度很高,但输出到 Simulink 的数据会按照你设置的采样时间进行插值。控制算法运行的周期一般取 10ms 到 50ms,也就是说控制算法每 10ms 或者 20ms 才计算一次方向盘转角。这里有一个工程结论:MPC 对模型精度的敏感度最高,因为 MPC 在每一个控制周期内做优化时,都是基于内部模型来预测未来一段时间的轨迹,模型一旦不准,预测的轨迹就不准,计算出来的最优控制序列也就跟着跑偏。LQR 的敏感度相对低一些,因为它本质上是反馈闭环,每一步都测量当前状态做增益计算,模型不准顶多导致增益不是最优,但发散的可能性较低。纯跟踪则更依赖预瞄距离的选取,对模型精度要求其实不算高,它更多是几何方法。
3. 控制算法选型:纯跟踪、LQR、MPC 的对比与选型理由
3.1 三种算法在同一工程框架下的定位差异
这个项目最核心的价值就是“对比”。我把三种算法的工程定位先说一下:
| 算法 | 核心思想 | 计算复杂度 | 约束处理能力 | 适用工况 |
|---|---|---|---|---|
| 纯跟踪 | 几何追踪预瞄点 | 极低 | 无 | 低速、曲率变化平缓路径 |
| LQR | 线性状态反馈最优控制 | 低 | 无(可限幅) | 中高速、稳定性优先 |
| MPC | 滚动时域优化 | 高 | 强(输入约束、状态约束) | 高速、急转弯、复杂路径 |
纯跟踪把一个控制问题简化成一个几何问题,从车辆当前位置出发,沿目标轨迹向前找一个预瞄距离 (L_d),然后计算出为了到达这个预瞄点所需要的圆弧曲率,再由曲率反算出前轮转角。它的优点是极简单、极稳定、极容易实现,缺点是预瞄距离 (L_d) 的选取对效果影响很大,车速越高需要的预瞄距离越长,而预瞄太长会导致切弯。LQR 的核心是把模型在某个工作点线性化,构建一个状态反馈控制器,通过最小化一个无限时域的二次型性能指标来求取最优反馈增益。MPC 则是每次控制周期都求解一个有限时域的优化问题,目标函数同时包含跟踪误差、控制量幅值和控制量变化率惩罚,并能显式地处理前轮转角限位和前轮转角变化率限位。
3.2 纯跟踪算法的实现细节与预瞄距离标定
纯跟踪算法的核心公式是这样:
[ \delta = \arctan\left(\frac{2 L \sin(\alpha)}{L_d}\right) ]
其中 (\delta) 是前轮转角,(L) 是轴距,(\alpha) 是车辆当前航向与预瞄方向之间的夹角,(L_d) 是预瞄距离。这个公式的推导基于阿克曼转向几何,认为车辆沿圆弧运动时,圆弧半径 (R) 满足关系 (L_d = 2R \sin(\alpha)),再由车辆运动学关系得到上式。
工程实现时,预瞄距离 (L_d) 通常取为:
[ L_d = k_d v_x + L_{d0} ]
其中 (k_d) 是预瞄时间系数,一般取 0.1 到 0.5 秒,(L_{d0}) 是基础预瞄距离,一般取 2 到 5 米。我在实际调参中发现,车速 30km/h 的时候,(k_d=0.2) 秒、(L_{d0}=3) 米效果不错;车速 80km/h 的时候,预瞄距离必须加大到 15 米以上,否则车辆会出现明显的蛇形。纯跟踪在低速下非常好用,但速度一高,横向误差就有明显的稳态趋势,因为它本质上是“看一个点走”,缺少对路径未来变化的提前预判。
3.3 LQR 的设计流程与权重矩阵调参思路
LQR 的设计流程比较固定。第一步是把车辆动力学模型写成状态空间形式:
[ \dot{x} = A x + B u ]
其中状态量 (x) 通常取横向偏差、横向偏差变化率、横摆角偏差、横摆角速度,控制量 (u) 取前轮转角。第二步是确定性能指标:
[ J = \int_{0}^{\infty} (x^T Q x + u^T R u) dt ]
第三步是通过求解代数黎卡提方程得到最优反馈增益矩阵 (K),控制律为 (u = -K x)。
权重矩阵 (Q) 和 (R) 的调参是最常见的坑。我的经验是:先固定 (Q) 的对角元素,优先把横向偏差的权重调大(比如设为 5 到 10),然后逐步增加横摆角偏差权重,最后调整 (R)。(R) 不能太小,否则前轮转角会非常敏感,方向盘会剧烈抖动;但 (R) 也不能太大,否则跟踪误差会明显增大。我的一个实用经验是:(R) 的数量级通常比 (Q) 中横向偏差权重要小 2 到 3 个数量级,就是说如果横向偏差权重取 5,(R) 可以取 0.01 到 0.05。这里存在一个数学上的平衡关系:(Q) 和 (R) 的相对大小直接决定了控制能量和跟踪精度之间的取舍,调参的本质就是在“使劲打方向减少误差”和“少打方向保持舒适”之间找一个平衡点。
3.4 MPC 的预测模型、约束设计与求解器配置
MPC 在工程上比前两种算法高一个段位,因为它能做“带约束的最优控制”。在这个项目里,MPC 的控制周期一般取 20ms 到 50ms,预测时域取 10 到 30 步,控制时域取 3 到 10 步。预测模型仍然是自行车模型,但是需要离散化成线性时变形式:
[ x_{k+1} = A_k x_k + B_k u_k ]
在每个控制周期里,MPC 求解如下优化问题:
[ \min_{u_0,...,u_{N-1}} \sum_{k=0}^{N-1} \left( x_k^T Q x_k + u_k^T R u_k + \Delta u_k^T S \Delta u_k \right) ]
约束条件包括:
[ u_{min} \leq u_k \leq u_{max} ]
[ \Delta u_{min} \leq \Delta u_k \leq \Delta u_{max} ]
(u_{min}) 和 (u_{max}) 对应前轮转角物理限位,一般乘用车在正负 30 度到 40 度之间。(\Delta u) 约束对应方向盘转角变化率的限制,这个约束如果设得太紧,车辆在紧急避障时会显得“反应迟钝”;设得太松,方向盘又容易出现高频抖动,实车上是绝对不能接受的,但在仿真阶段很多人会忽略。MPC 在 Carsim 联合仿真中控制效果看起来最好的原因不仅是它有约束处理能力,更重要的是它每次都在重新预测和重新优化,控制序列具有滚动更新的自我纠错能力。
3.5 三种算法在项目指标体系下的对比维度
项目里进行对比时,不能只看横向误差一个指标。我建议至少从四个维度评估:
- 横向误差的最大值(峰值跟踪能力,反映避障或过急弯时的极限偏差)
- 横向误差的均方根值(综合跟踪精度,反映全程平均表现)
- 前轮转角控制的平顺性(控制量变化率的最大值和标准差,反映执行器磨损和乘坐舒适度)
- 算法单步计算耗时(反映实时性,为后续硬件在环 HIL 或实车控制器部署做评估)
这个项目跑下来,在常规工况下 MPC 的横向误差均方根值通常比 LQR 低 30% 到 50%,比纯跟踪低 60% 到 80%。但在平滑路径上,LQR 的控制量平顺性往往最好,因为 MPC 的约束边界在起作用时,控制量变化率会出现阶段性跳变。纯跟踪在中低速简单路径上的表现并不差,计算耗时几乎可以忽略不计。这些结论在下面的仿真实例里会清楚地体现出来。
4. Carsim 与 Simulink 联合仿真环境搭建:从车辆配置到接口打通
4.1 Carsim 车辆模型参数配置与数据准备
搭建联合仿真环境,第一步是配置 Carsim 车辆模型。以一款中型轿车为基准,我用的参数大致是:整车质量 1500kg,前轴到质心距离 1.1m,后轴到质心距离 1.6m,轴距 2.7m,前轮侧偏刚度约 80000N/rad,后轮侧偏刚度约 100000N/rad,质心高度 0.55m,轮距 1.5m。当然实际车的侧偏刚度不是一个固定值,Carsim 里面提供了完整的轮胎表,可以查不同载荷、不同侧偏角下的侧偏力。
需要重点注意的一个参数是“质心到前轴距离”和“质心到后轴距离”。这两个参数加上车速,直接决定了车辆横摆响应的固有频率和阻尼比,进而影响所有控制算法里车辆模型的准确性。在 Carsim 里有一条便捷做法:先在车辆参数页面确认好轴距和质心位置,再把前轮侧偏刚度与后轮侧偏刚度的比值调成与真实工况匹配。如果你发现 LQR 在高速仿真中车辆横摆振荡、误差发散,先别急着怀疑算法,去检查一下模型参数是不是和控制算法内部模型差得太多。
4.2 Simulink 模型接口配置与控制算法集成
Carsim 和 Simulink 联合仿真的核心是通过一个 S-Function 接口模块实现数据交换。Carsim 输出的信号一般包括车辆纵向速度、横向速度、横摆角速度、全局坐标系下的位置 X 和位置 Y、横摆角等。Simulink 输入给 Carsim 的信号一般是前轮转角和驱动力矩或油门信号。接口模块的方法是:在 Simulink 中拖动 Carsim S-Function 模块,双击打开配置界面,选择一个已经生成好的 Carsim 仿真数据库文件(.sim 或 .par 文件),然后启动 Carsim 中的 Simulink 联合仿真选项。
实际工程中常遇到的一个情况是,Carsim 库文件路径必须在 Matlab 的当前路径中可见,否则 S-Function 模块会报错“无法找到模型文件”。这个报错不算致命,但很烦人,解决方案是使用绝对路径并且把路径加入 Matlab 的 path 环境。另一个坑是 Carsim 中仿真时间设置一定要和 Simulink 中的仿真停止时间一致。曾经有人在这上面浪费过半天时间——Carsim 只仿真了 5 秒,Simulink 跑到 10 秒,后半程数据全是常数零。
4.3 期望轨迹生成模块的编写
期望轨迹是本项目里容易被低估的一部分。我建议用 Matlab 脚本生成期望轨迹数据,再通过 Lookup Table 模块导入 Simulink。这样做的好处是轨迹可复用、可修改、可对比,不同路径的测试都统一走同一个模块。
以双移线路径为例,可以用如下思路生成轨迹:
vx = 72 / 3.6; % 车速 72 km/h t = 0:0.01:15; % 仿真时间 15s s = vx * t; % 纵向位置随时间变化 % 双移线的横向位移设计 Y = zeros(size(s)); % 在特定纵向区段内插入正弦过渡曲线 idx1 = s >= 20 & s < 40; idx2 = s >= 40 & s < 60; Y(idx1) = ...; % 第一个偏移段 Y(idx2) = ...; % 第二个偏移段 % 计算期望横摆角(近似:dY/ds) psi_ref = atan2(gradient(Y), vx * 0.01);需要明确:期望轨迹可以生成在全局坐标系下,车辆的实际位置也由 Carsim 输出在全局坐标系下。那么横向误差的计算就需要做一个坐标系变换:
[ e_y = -\sin(\psi_{ref}) (X_{veh} - X_{ref}) + \cos(\psi_{ref}) (Y_{veh} - Y_{ref}) ]
这个公式是联合仿真项目里最容易出错的地方之一。坐标变换做错了,横向误差符号会反,或者误差幅值会成倍跳变,而不会为零。我通常建议先在 Matlab 里单独验证轨迹生成脚本和误差计算函数,再放进 Simulink,这样能避免把两个模块的问题混合在一起排查。
4.4 仿真工况设置:双移线、蛇形路径与定曲率弯道
仿真工况的设计直接决定了对比结论的有效性。我给这个项目设计了三种典型工况:
| 工况 | 速度区间 | 路径特征 | 考察点 |
|---|---|---|---|
| 双移线 | 60-80 km/h | 先向左再向右连续换道 | 避障场景下的瞬态跟踪能力 |
| 蛇形路径 | 30-50 km/h | 周期性正弦转向 | 连续转向下的稳定性与控制平顺性 |
| 定曲率弯道 | 60-100 km/h | 曲率恒定圆弧 | 稳态跟踪精度与弯道速度适配性 |
双移线工况(ISO 3888 风格)是车辆稳定性测试的经典工况,它能考察车辆在剧烈变向时的横向误差峰值,同时能暴露算法是否产生激进的转向动作。蛇形路径更像日常行驶中连续变道的场景,周期性的转向输入会让车辆的横摆响应出现相位滞后,控制算法的“预判能力”在这里体现得最明显。定曲率弯道看似简单,却最能反应算法的稳态跟踪误差——纯跟踪在定曲率弯道上容易出现固定数值的稳态横向偏差,而 MPC 因为预测到了未来轨迹的曲率,稳态误差基本可以收敛到零附近。
三种工况全部跑完后,把误差数据导出到 Matlab workspace,再用统一的脚本计算性能指标。这里有一个很好的做法:把三种算法的性能指标输出到同一个结构体中,再写一个绘图函数把误差对比曲线统一绘制。这样图表的表达力远比零散截图强,论文里也好用。
5. 仿真结果深度解读:从误差曲线到控制行为的差异分析
5.1 双移线工况下的横向误差与控制量特征
双移线工况我从 72km/h 的速度开始跑,目标轨迹是在纵向 0-120m 范围内完成一次模拟高速公路避障的侧向偏移。先看纯跟踪算法:横向误差曲线的特征是一个典型的“时间滞后误差”——入弯初期误差为正(车辆在目标轨迹内侧),出弯时误差为负(车辆冲出目标轨迹外侧),峰值误差约 0.8m。这个数值在真实高速公路工况下是绝对不可接受的,但作为低速泊车场景的表现,已经够用。
LQR 算法的峰值误差大概在 0.35m,比纯跟踪好了不止一个量级。但 LQR 在双移线的第二个移线阶段出现了一个有意思的现象:控制量曲线有一个明显的反向峰值,也就是在目标轨迹从向左变成向右的瞬间,方向盘先猛打了一个反方向角度。原因在于 LQR 是一个线性反馈控制器,它不对未来轨迹做预测,当误差突然反向时,状态量的变化立刻反应到控制量上,这个“控制滞后”在物理上表现为车辆轨迹的“切弯”现象。
MPC 在同样的双移线工况下,峰值误差大约 0.18m,控制量也更加平滑。一个关键原因是 MPC 的预测时域覆盖了整个双移线过渡段,它在进行第一段偏移时就已经预见了第二段反向偏移,因此在误差出现反向之前就逐渐减少了控制量的幅值。方案实现了“路径预判”,效果自然好。
5.2 定曲率弯道的稳态误差论证
定曲率弯道工况能很清楚地说明“预判”的价值。半径为 80m 的圆弧,以 60km/h 的速度跟踪。纯跟踪在这个工况中呈现出一个恒定的稳态横向误差:车辆在弯道内侧稳定偏移,偏移量与预瞄距离 (L_d) 直接相关。(L_d) 越大,稳态误差越大,但动态调节过程越平缓;(L_d) 越小,稳态误差越小,但容易产生蛇形振荡。这个trade-off是纯跟踪无法同时解决的。
LQR 的稳态误差比纯跟踪小得多,大约在 0.05m 量级,原因在于 LQR 是积分意义上的最优控制,它能保证系统在常值扰动下状态收敛。但严格讲 LQR 在定曲率弯道下是存在稳态误差的,因为它的模型是线性定常的,外部的曲率输入可以被等效成一个常值扰动。如果要完全消除稳态误差,工程做法是在状态反馈中加入积分项,或者在前馈通道中显式加入曲率补偿项。我在项目实现中发现,(u = -Kx + \delta_{ff}) 和 (u = -Kx) 在定曲率弯道上横向误差可以差出三倍。
MPC 在定曲率弯道上的稳态误差几乎为零,原因是 MPC 的目标函数中包含了对未来曲率的预测,当预测轨迹与目标轨迹重合时,系统找到了一个稳态平衡点。这里必须补充一个重要结论:稳态误差为零并不代表物理上方向盘转角为零,弯道中 MPC 输出的前轮转角大约是 2.8 度,这是一个“前馈控制量”和“反馈修正量”叠加的结果。
5.3 算法计算耗时与实时性评估结果
在这个项目里,我用 Matlab 的 tic/toc 和 Simulink 的时间戳测了三种算法的单次控制周期计算耗时。测试环境是一台中端配置的笔记本,Matlab 版本为 R2022a。在同样的预测时域设置为 20 步、控制时域为 5 步的条件下:
| 算法 | 平均单步计算耗时 | 实时性评价 |
|---|---|---|
| 纯跟踪 | 约 0.2ms | 极强,任何实时环境均可运行 |
| LQR(含黎卡提求解) | 约 0.8ms | 强,嵌入式控制器轻松运行 |
| MPC(基于 quadprog) | 约 12-35ms | 勉强实时,需代码优化或专用求解器 |
这里的 MPC 耗时会随着约束条件激活状态波动。当车辆在中低速无急转弯工况时,优化问题约束不激活,计算耗时接近下限;当车辆进入紧急避障工况,转向约束被激活后,求解迭代次数增加,耗时明显上升。在实际做实时系统部署时,MPC 通常会使用基于快速梯度法或者内点法的嵌入式求解器,替代 Matlab 环境的 quadprog 求解器,能把单步耗时压到 2ms 以下。这同时也说明,项目里 MPC 效果好是付出了计算代价换来的,这份账要算清楚。
6. 常见问题排查与避坑实操手册
6.1 联合仿真模型不匹配导致的结果发散
我遇到的第一个大坑就是 Carsim 车辆模型参数和 Simulink 控制算法内部模型参数不匹配。具体表现是 LQR 在低速工况下表现正常,但是车速一超过 80km/h,前轮转角就开始振荡,横向误差直接发散。
排查思路是这样:先检查 Simulink 模型中的状态空间矩阵 A 和 B 是否随车速变化而更新。很多初学者把 A 和 B 矩阵设成常量——这在固定车速仿真里没问题,但如果仿真过程中车速在变化,常量模型迟早出问题。解决方案是使用 Simulink 的 S-Function 或者 Matlab Function 模块,在每个控制周期根据当前车速重新计算 A 和 B 矩阵。这个看似复杂的操作,实际上只需要写一个二三十行的函数就能实现。
还有一个经验:如果你发现 LQR 的控制量在初始时刻有一个巨大的跳变,多半是车辆模型里的初始横摆角和目标轨迹的初始横摆角不一致。解决办法是在仿真开始前,把车辆初始位置和航向设置成与轨迹起点完全一致,或者在控制器运行时对误差初始值做软启动处理(对控制量做低通滤波),这样能避免起始瞬间的转向冲击。
6.2 MPC 求解失败与约束冲突问题
MPC 的求解失败是最让人头疼的。表现是 Simulink 仿真中途报错“QP problem is infeasible”或者是开始输出 NaN 的控制量。原因一般是约束条件过严。比如前轮转角约束设为正负 25 度,但在紧急避障时 MPC 计算出需要 30 度的前轮转角才能跟踪上目标轨迹,问题就无解了。工程上解决方案有三种:一是放宽约束限位;二是在目标函数中加入松弛变量(slack variable),允许约束在极端情况下被适当放宽;三是缩短预测时域,因为预测时域越长,越容易遇见不可达状态序列。
另外还有一种情况容易被忽略:控制时域和预测时域设置不合理。比如预测时域设为 30 步但控制时域只有 1 步,MPC 几乎退化成一步最优预瞄,跟踪精度大幅下降。我的建议是保持预测时域不小于控制时域的 5 倍,这个比例在车辆横向控制中基本都是安全且有效的。
6.3 轨迹跟踪误差在直线段不为零的问题
在实际调试中我发现一个怪现象:车辆在进入直线段后,横向误差不能完全收敛到零,而是一个几十厘米的常数偏置。一开始我以为是坐标变换误差,检查了好几遍发现算法逻辑没有错。后来发现问题是目标轨迹生成时,仿真步长不够细,期望轨迹点之间的间距过大,导致在直线和曲线衔接处轨迹变成了折线。车辆在折线段行驶时,LQR 和 MPC 需要不断修正方向,但纯几何上的折线误差始终存在。
解决方案很简单:把轨迹生成脚本的步长从 0.1s 提高到 0.01s,重新生成轨迹后问题消失。另一个原因是期望横摆角的计算方式,如果把期望横摆角直接取为相邻轨迹点连线方向与全局 X 轴的夹角,那么轨迹点越稀疏,角度量化误差越大。需要做进一步的平滑处理,比如使用滑动窗口平均或样条插值。
6.4 软件版本兼容性注意事项
这个项目对 Matlab 和 Carsim 的版本兼容性要求比较苛刻。Carsim 通过 S-Function 和 Simulink 通信时,不同的 Carsim 版本对 Matlab 版本有明确的适配关系。只要版本不兼容,S-Function 编译时就会出现链接错误或者运行时报错。
建议动手之前先查询 Carsim 官方兼容性列表,确认好版本对应关系再搭环境。另一个靴子落地是 64 位系统和 32 位编译器的搭配问题:Matlab 在 Windows 上编译 C Mex 文件需要配置好 C 编译器环境,如果之前没配置过,建议先在 Matlab 命令行运行 mex -setup 完成配置,再运行 Carsim 的接口模块。我见过不少人在这一步直接被劝退,本以为是模型问题,结果仅仅是因为编译器没配置。
7. 实战经验总结与后续扩展方向
整套联合仿真跑下来,我的一个核心体会是:横向轨迹跟踪没有绝对最优的算法,只有针对特定工况和需求的最优选择。纯跟踪的低计算量在工程部署中依然是启动阶段执行器控制的保底方案,在低速泊车、农机导航等场景下依然大量使用;LQR 以极低的计算成本提供了不错的中高速跟踪品质,在实际量产控制器中被用作主要横向控制器的例子非常多;MPC 的效果最好,约束处理能力强,但计算量、调参复杂度和实时性要求都高,目前在高端车型和自动驾驶系统上更常见。
从项目扩展角度看,这个框架还能顺延出很多有价值的方向:在 MPC 的代价函数里加入舒适性指标(如加加速度惩罚),可以有效抑制方向盘抖动;把纯跟踪和 MPC 结合,用纯跟踪结果为 MPC 提供初值,能够显著缩短求解时间;给 LQR 增加自适应增益调度的功能,用查询表实现在不同车速下切换不同增益,是工程中最实用的 LQR 写法;还可以加入侧偏角限制作为状态约束,防止轮胎工作在非线性区,这对高速低附着路面的安全控制意义重大。
项目代码在复现时,建议保留每次仿真跑出的数据文件,把三种算法的结果做成统一格式的 mat 文件存储。后续做统计分析和图表绘制时,不仅省事,也方便对比多次调参后的差异。我自己的习惯是每跑完一组实验,就用一个脚本把误差峰值、均方根值、控制量标准差、单步耗时四个指标打印出来,然后归档到实验记录里。长期积累下来,你会对每个参数变化对结果的影响形成一套非常敏锐的直觉,这种直觉比任何理论推导都来得实用。
最后再分享一个细节:Carsim 的车辆模型在联合仿真中默认是会受到风阻和滚动阻力影响的,而这些阻力项在你控制算法的模型里往往不存在。这意味着控制器在巡航时需要额外克服一个“阻力扰动”,纯跟踪和 LQR 由于缺少预测,会把这个扰动当成误差来处理。如果你想精确对比算法,建议在 Carsim 中关闭风阻和轮胎滚动阻力。等到算法对比完成,再打开这些阻力项,用来测试算法对未建模扰动的鲁棒性。这个小小的开关,能让你的对比结论更干净,也能让你的算法抗扰测试更有说服力。