路径规划算法全解析:从A*、RRT到DWA与MPC的工程实践

1. 项目概述:从“寻路”到“规划”的思维跃迁

在机器人、自动驾驶、无人机乃至游戏开发领域,“路径规划”都是一个绕不开的核心议题。它远不止是“找一条从A到B的路”那么简单。想象一下,你开车去一个陌生的商场,手机导航会给你规划路线,但当你开到商场门口,面对复杂的内部通道和拥挤的车位,导航就基本“哑火”了。这时,你需要的是另一种“规划”能力——如何安全、高效、合规地停进那个狭小的车位。这就是路径规划算法从宏观走向微观、从全局走向局部的典型场景。我们常说的“各类路径规划算法”,本质上是一套工具箱,针对不同尺度、不同约束、不同实时性要求的场景,提供了不同的解决方案。今天,我们就来系统性地拆解这个工具箱,看看里面到底有哪些“神兵利器”,以及它们各自在什么场合下最能大显身手。无论是研究算法的学生,还是需要落地应用的工程师,理解这套分类和选型逻辑,都能让你在面对具体问题时,不再盲目地“试遍所有算法”,而是能够精准地“拿起对的工具”。

2. 路径规划算法的核心分类与选型逻辑

路径规划算法种类繁多,但杂乱无章地罗列并无意义。一个资深的从业者在接触新问题时,第一反应一定是分类和选型。我们可以从几个最关键的维度对算法进行划分,这直接决定了你的技术方案是否合理。

2.1 按环境认知程度划分:全局规划与局部规划

这是最根本的分类方式,决定了算法的输入和信息基础。

全局路径规划的特点是“上帝视角”。算法在执行规划前,就已经掌握了整个环境的完整、准确的先验地图。比如室内的建筑平面图、城市的道路网数据、已知的障碍物位置等。这类算法的任务是,在这个静态的全局地图上,找出一条从起点到终点的最优或次优路径。它的结果通常是一条宏观的“参考线”或“走廊”,不处理动态的、未知的障碍。常见的A*Dijkstra快速随机搜索树(RRT)及其变种(如RRT*),以及基于图搜索的算法,都属于全局规划器。它们好比是出行前在手机地图上做的行程规划,告诉你大体怎么走,但无法应对路上突然出现的施工或事故。

局部路径规划则恰恰相反,它处于“第一人称视角”。算法没有完整地图,或者即使有全局地图,也需要依赖实时传感器(如激光雷达、摄像头、超声波)来感知周围局部环境的动态变化。它的核心任务是,在全局路径(或目标方向)的指导下,进行实时避障和轨迹生成,应对突然出现的行人、车辆、临时障碍等。动态窗口法(DWA)人工势场法时间弹性带(TEB)以及模型预测控制(MPC)等,都是典型的局部规划器。它们就像是驾驶员的眼睛和大脑,在按照既定路线行驶时,实时处理方向盘和刹车的微操。

选型心得:绝大多数成熟的移动机器人系统(如扫地机器人、仓储AGV、自动驾驶汽车)都采用“全局规划 + 局部规划”的分层架构。全局规划器给出粗粒度路径,局部规划器负责跟踪这条路径并实现实时避障。二者相辅相成,缺一不可。试图用一个算法解决所有问题,往往会在复杂动态环境中碰壁。

2.2 按算法原理划分:基于搜索、基于采样、基于优化与基于学习

这个维度揭示了算法的内核思想,帮助你理解其性能边界。

基于搜索的算法:将环境离散化为图(Grid Map)或网格,然后在图上执行搜索。Dijkstra算法是鼻祖,保证找到最短路径,但效率较低。A*算法通过引入启发式函数(估计到终点的代价),极大地提高了搜索效率,是应用最广泛的全局规划算法之一。它的变种如D*LPA*等,还能处理动态变化的图权重,适用于环境部分已知的场景。这类算法的优点是原理直观、解的最优性有保障,但缺点是对高维状态空间(如考虑姿态)和连续空间的处理能力有限。

基于采样的算法:为了克服“维度灾难”,这类算法通过在状态空间中随机采样来构建一棵搜索树(如RRT)或一个图(如PRM),而不需要显式地对整个空间进行建模。RRT(快速随机搜索树)及其最优性版本RRT*非常著名,特别适合在高维空间(如机械臂规划)和复杂几何环境中进行规划。它们通常能快速找到一条可行路径,但不一定是最优的,且路径可能比较“迂回”和“抖动”,需要后处理平滑。

基于优化的算法:将路径规划问题形式化为一个数学优化问题,通过最小化某个目标函数(如路径长度、平滑度、能耗、与障碍物的距离)来求解。局部规划中的DWA、TEB和MPC本质上都是优化器。例如,TEB将路径和速度同时作为优化变量,在满足动力学约束和避障约束的前提下,优化总时间。这类方法的优点是能直接生成平滑、符合动力学约束的轨迹,非常适合高速移动的机器人,但计算量较大,且对初始值和约束建模非常敏感。

基于学习的算法:这是近年来的热点,尤其是深度强化学习(DRL)。算法通过与仿真环境的大量交互,学习到一个“策略”网络,直接根据当前状态(传感器输入)输出动作(控制指令)。它能够处理非常复杂的感知-决策映射,甚至能学会一些“炫酷”的避障技巧。但缺点同样明显:需要海量的训练数据和计算资源,训练的稳定性差,“黑箱”特性导致可解释性和安全性验证困难。目前更多处于研究和特定场景(如游戏、仿真)应用阶段,在安全苛求的领域(如乘用车自动驾驶)落地仍需时日。

2.3 按应用场景聚焦:从无人机到自动泊车

不同的应用场景对算法提出了截然不同的要求,这也是“算法大全”必须结合场景来谈的原因。

无人机路径规划:无人机通常在三维空间中运动,规划时需要考虑高度、空域限制、能耗(与风速风向相关)等因素。算法需要处理三维空间的避障和效率问题。此外,无人机对实时性要求高,且可能面临GPS信号丢失的情况(视觉/激光SLAM建图与规划结合)。RRT* 系列算法在三维路径规划中很常见,也有研究将A*扩展到3D网格。对于集群无人机,还需要考虑协同路径规划,避免碰撞和优化整体任务完成时间。

自动驾驶路径规划:这是最复杂的场景之一,通常分为三层:任务规划(从A城市到B城市,类似导航)、行为规划(何时换道、超车、路口通过)和运动规划(生成车辆可执行的具体轨迹)。在运动规划层,又分为全局轨迹规划(在车道级地图上生成参考线)和局部轨迹规划。局部轨迹规划常采用“Frenet坐标系”下的优化方法,将道路中心线作为参考,在横向和纵向上分别规划,并结合速度规划,生成时空联合的轨迹。优化目标包括舒适性(加速度/加加速度小)、安全性(远离障碍物)、合规性(遵守交规)和进度(尽快到达)。

自动泊车路径规划:这是一个典型的非结构化环境、高精度、强约束的规划问题。泊车空间狭窄,车辆运动学模型(非完整约束)必须被精确考虑,规划出的路径必须能让车辆通过前轮转向实现。常见的算法是基于几何的解析方法基于优化的搜索方法。解析方法通过计算几个关键圆弧和直线的组合(如“一把舵”、“倒车入库”的标准几何路径)来生成路径,速度快但适应性有限。而基于Hybrid A*的搜索方法则更为强大:它在连续的状态空间(x, y, 航向角)中进行离散搜索,每一步都考虑车辆的真实运动学模型(如阿克曼转向),因此生成的路径天然就是车辆可执行的。搜索完成后,再用数值优化方法(如二次规划QP)对路径进行平滑,确保方向盘转动不会太突兀。这就是为什么“泊车路径规划算法”和“局部路径规划算法 qp”这两个热词经常关联在一起——QP是泊车和局部规划中用于轨迹平滑和后处理的利器。

机器人室内导航:对于扫地机器人、服务机器人等,环境通常是结构化的室内。SLAM建图后,使用A*进行全局规划是标准操作。局部规划则广泛采用DWA算法。DWA的原理非常直观:在机器人的速度空间(线速度和角速度)中采样多组速度对,模拟这些速度在短时间(例如0.5-1秒)内产生的轨迹,然后用一个评价函数给每条轨迹打分。评价函数通常包括:朝向目标的程度、与障碍物的距离、当前速度等。最后选择得分最高的轨迹对应的速度来执行。DWA实时性好,能有效应对动态障碍,是轮式机器人局部避障的“老兵”。

3. 核心算法深度解析与实操要点

了解了分类和场景,我们深入几个最具代表性的算法内核,看看它们具体如何工作,以及在实际编码和应用中需要注意什么。

3.1 A* 算法:全局规划的基石

A* 算法可以看作是Dijkstra算法的“智能”升级版。它的核心在于一个评价函数:f(n) = g(n) + h(n)

  • g(n)是从起点到节点n的实际代价。
  • h(n)是从节点n到终点的估计代价,这就是启发式函数。

算法维护两个列表:开放列表(待考察节点)和关闭列表(已考察节点)。它总是从开放列表中选取f(n)值最小的节点进行扩展,直到扩展到终点。

实操要点与坑点

  1. 启发函数h(n)的选择:这是A*的灵魂,也决定了效率和最优性。
    • 必须可采纳h(n)必须永远不大于从n到终点的真实代价。否则,A* 不能保证找到最优路径。对于二维网格,曼哈顿距离(只允许上下左右移动)和对角线距离是可采纳的;欧几里得距离(直线距离)也是可采纳的,且通常能提供更强的启发性,搜索节点更少。
    • 实际编码:在栅格地图中,计算欧氏距离需要开方,消耗较大。一个常见的优化是使用切比雪夫距离或预先计算好的距离查找表。
  2. 权重系数:有时为了更快找到路径(不一定最优),会使用加权A*:f(n) = g(n) + ε * h(n),其中ε > 1。这会让算法更“贪婪”地冲向目标,大幅减少搜索范围,但路径可能不是最优的。ε值越大,速度越快,路径可能越长。
  3. 地图表示与代价:栅格地图中,每个栅格的代价g(n)不一定是1。可以给草地、沙地设置更高的代价(如2或3),给道路设置低代价(如1),这样A*会自动规划出更“好走”的路径,而不仅仅是最短路径。
  4. 性能瓶颈:当地图很大时,开放列表的维护(频繁插入和取出最小值)会成为瓶颈。使用二叉堆(优先队列)来管理开放列表是标准做法。对于超大规模地图,可以考虑Jump Point Search (JPS)等优化算法,它能跳过大量不必要的节点,在均匀代价网格上比A*快一个数量级。
# A* 算法的简单框架示意(非完整代码) def a_star_search(start, goal, grid_map): open_set = PriorityQueue() open_set.put((0, start)) came_from = {} # 记录父节点,用于回溯路径 g_score = {start: 0} f_score = {start: heuristic(start, goal)} while not open_set.empty(): current = open_set.get()[1] if current == goal: return reconstruct_path(came_from, current) # 回溯得到路径 for neighbor in get_neighbors(current, grid_map): tentative_g_score = g_score[current] + cost(current, neighbor) if neighbor not in g_score or tentative_g_score < g_score[neighbor]: # 这是一个更好的路径 came_from[neighbor] = current g_score[neighbor] = tentative_g_score f_score[neighbor] = g_score[neighbor] + heuristic(neighbor, goal) if neighbor not in open_set: open_set.put((f_score[neighbor], neighbor)) return None # 未找到路径

3.2 RRT/RRT*:应对高维与复杂空间的利器

RRT(快速随机搜索树)的思路非常“暴力美学”:它不试图建模整个空间,而是通过随机采样来探索。

  1. 在地图中随机采样一个点q_rand
  2. 在已有的树中找到离q_rand最近的节点q_near
  3. q_nearq_rand的方向生长一段固定步长step_size,得到新节点q_new。检查q_nearq_new的连线是否碰撞。
  4. 若无碰撞,则将q_new加入树,其父节点为q_near
  5. 重复直到q_new接近目标点。

RRT* 是 RRT 的渐进最优版本。它在加入新节点q_new后,增加了一个“重布线”步骤:在以q_new为圆心、一定半径为邻域内,检查是否存在其他节点作为q_new的父节点时,能使q_new到起点的路径代价更小。如果是,则重连。同时,它还会尝试用q_new去优化邻域内其他节点的路径。

实操要点与坑点

  1. 步长选择:步长太大,容易碰撞,路径粗糙;步长太小,生长缓慢,在狭窄通道中尤其困难。一种自适应策略是:当多次生长失败时,临时减小步长。
  2. 目标偏置采样:纯粹的随机采样效率低下。常见的改进是,以一定概率(如5%)直接采样目标点作为q_rand,这能引导树向目标生长,加速收敛。
  3. 狭窄通道问题:RRT系列算法在狭窄通道中采样概率极低,可能导致规划失败。RRT-Connect(双向RRT)通过从起点和终点同时生长两棵树,并在中间对接,能有效缓解此问题。
  4. 路径后处理:RRT生成的路径像“树枝”,由许多直线段组成,转折尖锐,不适合机器人直接跟踪。必须进行后处理平滑。常用方法包括:
    • 剪枝:尝试连接路径中不相邻的节点,如果无碰撞则删除中间节点。
    • 插值平滑:使用样条曲线(如B样条)或多项式对路径点进行拟合,得到光滑曲线。
    • 用优化器平滑:将RRT的路径作为初始解,送入像梯度下降二次规划(QP)这样的优化器中,以路径平滑度、远离障碍物等为目标进行优化。这是工业界常见的做法。

3.3 动态窗口法(DWA):轮式机器人的实时避障“老兵”

DWA是一个典型的局部规划器,它直接在速度空间进行搜索和优化。

算法步骤

  1. 速度采样:根据机器人当前速度和电机性能,确定一个动态窗口[v_min, v_max],[ω_min, ω_max]。在这个窗口内离散采样多组(v, ω)
  2. 轨迹模拟:对每一组(v, ω),依据机器人的运动学模型,模拟其在未来一段时间(sim_time,如1秒)内的运动轨迹。
  3. 轨迹评价:用一个评价函数G(v, ω)给每条轨迹打分。评价函数通常包括:
    • heading(v, ω):轨迹末端朝向与目标点方向的偏差。
    • dist(v, ω):轨迹上离障碍物的最近距离。
    • velocity(v, ω):轨迹的速度大小(鼓励快速前进)。
    • 通常形式为:G = α*heading + β*dist + γ*velocity,权重系数需要调试。
  4. 选择执行:选择评价得分最高的(v, ω)发送给机器人底层执行器。

实操要点与坑点

  1. 评价函数的设计与调参:这是DWA的核心,也是最大的“玄学”。α, β, γ的权重直接决定了机器人的“性格”:是激进(偏向速度)还是保守(偏向距离)。dist(v, ω)项通常设计为:当距离大于安全阈值时,得分较高且平稳;当距离小于安全阈值时,得分急剧下降甚至为负,形成“悬崖效应”,强制避开。
  2. 振荡问题:机器人在狭窄通道或面对对称障碍时,容易在两条得分相近的轨迹间来回切换,导致运动振荡。解决方法包括:
    • 在评价函数中加入平滑项,惩罚与上一周期速度差异过大的选择。
    • 引入历史信息惯性,让当前评价略微偏向上一周期选择的速度。
  3. 局部最优与“死锁”:在复杂的U型或环形障碍中,DWA可能陷入局部最优,即所有模拟轨迹的评价都很低(比如都离障碍物太近),机器人因此停止不动。这时需要上层(如全局规划器或恢复行为)介入,比如让机器人原地旋转一定角度,或者执行一段预设的“逃生”动作,以跳出局部极小值。
  4. 与全局规划的配合:DWA需要一个目标点。这个目标点不应该是全局路径的终点,而应该是全局路径上、位于机器人前方一定距离(称为“前视距离”)的一个点。DWA会努力朝向这个局部目标点前进。同时,在评价函数中,heading(v, ω)项也应该计算的是与这条局部路径切向的夹角,而不是直接指向最终目标。

4. 前沿与融合:模型预测控制(MPC)与学习类算法

当问题约束越来越复杂,对动态性、平滑性要求越来越高时,基于优化的方法,特别是模型预测控制(MPC),显示出强大优势。

4.1 MPC在路径规划中的应用

MPC不是一个单一的算法,而是一种控制框架。它在路径规划中的核心思想是:

  1. 在每个控制周期,基于机器人当前的状态(位置、速度等)和动力学模型,对未来一段有限时间(预测时域)内的行为进行滚动优化
  2. 优化问题中包含了代价函数(跟踪参考路径、保持平滑、快速到达)和约束(速度/加速度极限、避免碰撞、遵守运动学模型)。
  3. 求解这个优化问题,得到未来一段时域内的最优控制序列(速度、转向指令)。
  4. 只取该序列的第一个控制指令执行。到下一个周期,用新的状态重新进行优化。

MPC的优势

  • 显式处理约束:可以将机器人的物理极限(最大速度、加速度、转向角)和安全性约束(与障碍物的最小距离)直接写入优化问题,这是基于搜索或采样的方法难以做到的。
  • 多目标优化:可以轻松地在代价函数中平衡路径跟踪精度、乘坐舒适性(加加速度)、能耗等多个目标。
  • 前馈能力:由于使用了模型进行预测,MPC对系统的动态变化有更好的前瞻性和适应性。

实操难点

  • 计算负担:在线求解一个(通常是非线性的)优化问题,计算量很大。对于高速移动的机器人,需要在几十毫秒内完成求解,对硬件和算法实时性要求极高。
  • 模型准确性:优化效果严重依赖系统动力学模型的准确性。模型失配会导致控制性能下降甚至不稳定。
  • 问题凸化:为了能快速求解,通常需要对非凸的避障约束进行凸化近似(例如,将机器人近似为圆形,或将障碍物膨胀为圆形),这可能会损失一些解空间。

4.2 学习类路径规划算法的现状与思考

深度学习,特别是深度强化学习(DRL),为路径规划提供了全新的思路:端到端地从感知输入映射到控制输出。

典型框架:智能体(机器人)观察环境状态s_t(可能是传感器原始数据或处理后的特征),根据策略网络π(a|s)选择一个动作a_t(如线速度、角速度)执行,环境转移到新状态s_{t+1}并给出奖励r_t。通过最大化累积奖励来训练策略网络。

优势与潜力

  • 处理复杂感知:可以直接处理图像、点云等原始数据,省去了传统方法中繁琐的特征提取和状态估计环节。
  • 涌现“智能”行为:在仿真中,DRL智能体可以学会非常灵活和拟人的避障策略,比如在人群中穿梭。
  • 适应未知环境:理论上,一个训练好的策略可以泛化到未曾见过的类似环境中。

当前主要挑战与落地瓶颈

  1. 样本效率与训练成本:DRL需要巨量的交互数据,在物理机器人上训练不现实,严重依赖仿真。而构建高保真、高效的仿真环境本身就是一个挑战。
  2. 安全性与可验证性:DRL策略是一个黑盒,其决策逻辑难以解释。在安全苛求的领域(如自动驾驶),无法严格证明其行为的安全性,这是阻碍其落地的最大障碍。
  3. 泛化与鲁棒性:在仿真中训练的策略,迁移到真实世界时,会因为传感器噪声、模型差异等出现性能下降(sim-to-real gap)。对环境中未见过的新奇障碍物(OOD)可能表现异常。
  4. 奖励函数设计:奖励函数如同“指挥棒”,设计不当会导致智能体学会“作弊”行为(如原地转圈以避免碰撞惩罚)。

当前可行的融合路径:目前更可行的方案是“学习与传统方法结合”,而非替代。例如:

  • 学习作为传统方法的组件:用神经网络来预测更准确的启发函数h(n)用于A*,或者学习一个更优的轨迹评价函数用于DWA。
  • 模仿学习:用传统方法或专家演示生成大量数据,训练一个神经网络来模仿这些“专家”行为,从而得到一个快速的前向推理策略,作为传统规划器的补充或后备。

5. 工程实践中的常见问题与排查技巧

理论再完美,落地时总会遇到各种问题。这里记录一些在真实项目中反复出现的“坑”和解决思路。

5.1 规划器无解或规划时间过长

现象:机器人“卡住”,规划器长时间不返回路径或返回失败。

排查思路

  1. 检查地图与代价地图:这是最常见的原因。确认输入给全局规划器的地图是否准确?障碍物膨胀半径是否设置得过大,导致可行区域被完全“堵死”?在ROS中,可以用rviz工具可视化costmap,检查机器人所在位置是否被标记为“致命障碍”(cost为254)。
  2. 检查起点和终点:起点或终点是否被放在了障碍物内部?有时定位漂移会导致起点被误判在墙上。可以尝试手动设置一个合理的起点和终点进行测试。
  3. 调整算法参数
    • A*类:检查启发函数权重ε。如果ε=1搜索慢,可以适当调大(如1.5或2)以获得次优但快速的路径。检查是否使用了JPS等加速算法。
    • RRT类:增加采样次数上限。调整步长,在狭窄区域尝试减小步长。启用目标偏置采样。尝试双向RRT(RRT-Connect)。
  4. 引入“恢复行为”:当规划失败时,不要让机器人傻等。设计一个恢复行为序列,例如:
    • 原地缓慢旋转一定角度,清除传感器可能被遮挡的视野。
    • 向后移动一小段距离,脱离可能陷入的凹形障碍区域。
    • 临时将局部代价地图中的一些动态障碍清除(假设其移动走了),再尝试规划。

5.2 路径抖动与机器人运动不平滑

现象:规划出的路径锯齿状严重,或者机器人跟踪路径时左右摇摆。

排查思路

  1. 路径后处理缺失或不当:对于RRT等算法生成的路径,必须进行平滑。检查平滑算法是否启用,参数(如平滑权重、曲率约束)是否合理。可以尝试不同的平滑器,如梯度下降平滑器或二次规划(QP)平滑器。
  2. 局部规划器参数问题
    • DWA:检查sim_time(模拟时间)和sim_granularity(模拟步长)。sim_time太短,规划器短视;太长,计算负担重且预测不准。调整轨迹评价函数的权重,增加对路径对齐度(heading)和平滑度(速度变化)的权重。
    • TEB/MPC:检查优化目标中平滑项(加速度、加加速度)的权重是否足够大。检查求解器的迭代次数和精度是否足够。
  3. 控制频率与规划频率不匹配:局部规划器以10Hz频率规划,但底层控制器以50Hz频率执行。如果规划器输出的速度指令本身就不平滑,控制器再快也无法弥补。确保规划器输出的指令序列是平滑的,或者让控制器进行插值。

5.3 在动态环境中表现不稳定

现象:机器人对突然出现的动态障碍物反应过激(急停)或迟钝(撞上)。

排查思路

  1. 传感器数据处理与代价地图更新:检查激光雷达等传感器的数据是否延时过大?代价地图中障碍物的膨胀层设置是否合理?膨胀半径应略大于机器人轮廓半径,为控制和规划误差留出余量。动态障碍物的标记和清除是否及时?通常会给动态障碍物一个衰减时间,避免其瞬间消失导致规划穿过该区域。
  2. 局部规划器预测能力:DWA只模拟了固定时间内的轨迹,无法预测动态障碍物的未来位置。可以引入简单的预测模型,例如假设动态障碍物保持当前速度匀速运动,在轨迹评价时,计算模拟轨迹与预测障碍物位置的时空交集。
  3. 引入“安全停止”轨迹:在DWA的轨迹评价中,强制加入一条以最大减速度停止的轨迹。如果其他所有轨迹的评价都很差(危险),就选择这条安全停止轨迹,让机器人先停下来,再思考下一步。

5.4 特定场景失败:狭窄通道与门廊

现象:机器人在通过狭窄通道或门时,容易在门口“犹豫”甚至撞到门框。

排查思路

  1. 精确的机器人轮廓建模:在代价地图中,用于膨胀障碍物的机器人轮廓模型是否准确?如果使用圆形近似,在通过窄道时可能会过于保守。使用更精确的多边形或网格模型,并配合合适的膨胀策略。
  2. 调整局部规划器行为
    • 在接近狭窄通道时,可以临时调低机器人的最大速度,让规划和控制更谨慎。
    • 调整DWA的评价函数,在接近目标时,降低速度项的权重,提高对齐目标方向(heading)的权重,让机器人更准确地对准通道中心。
  3. 行为层策略:这不是纯粹的规划问题,需要行为层配合。可以设计一个“通过门廊”的行为状态,在此状态下,规划器切换为一组更保守的参数,并且可能结合特定的感知处理(如识别门框),待通过后再恢复常态。

路径规划算法的选择和调优,永远是一个在性能(速度、最优性)安全性(避障)资源消耗(计算量)之间做权衡的艺术。没有“最好”的算法,只有“最适合”当前场景和约束的算法。理解每个工具的原理、优势和短板,结合实际需求进行组合、调整和创新,才是工程师的核心价值所在。这份“大全”提供了一个地图和工具箱,真正的探索之旅,从你面对具体问题的那一刻才刚刚开始。