Fast Planner规划算法(一)—— Fast Planner前端

news2024/12/23 9:26:58

   本系列文章用于回顾学习记录Fast-Planner规划算法的相关内容,【本系列博客写于2023年9月,共包含四篇文章,现在进行补发第一篇,其余几篇文章将在近期补发】

   一、Fast Planner前端

   Fast Planner的轨迹规划部分一共分为三个模块,前端采用Hybrid A* 算法生成比较粗糙的路径\轨迹,然后采用后端对前端生成的路径进行更加细致的处理和优化。

在这里插入图片描述

   本部分内容对前端进行介绍,Hybrid A* 算法的原理在前面的文章中已经介绍过了,这里主要介绍在Fast Planner中具体使用的一些流程和细节。

在这里插入图片描述
在这里插入图片描述

   Fast Planner中 Hybrid A* 算法的主要流程如下:

   在每轮循环中,首先会从优先队列中拿出新的节点 n c n_c nc,并判断该节点是否为终点以及从该节点能不能直接生成到终点的路径(比如采用Reeds sheep算法),若是,则规划结束返回路径,若不是则继续进行本轮循环

   在该新节点 n c n_c nc处向外拓展生成一些小的轨迹,这些小轨迹称为primitive,它们的末端就是拓展出来的节点,然后进行剪枝操作,如果有多个节点落在同一个栅格中,仅保留一个,讲这些新拓展出来的节点存放在nodes中。

   然后对nodes中的每个节点的质量进行评估(伪代码8-16行),对于每个节点,首先检查其是否已经在已经拓展过的闭集合中以及是否是可行节点(在边界范围内、不与障碍物碰撞等),

   若在闭集合或不是可行节点,则结束对这个节点的评估,继续进行下一个节点的评估。若不在闭集合中且为可行节点,则继续进行该节点的评估,计算该节点的g值,即其父节点 n c n_c nc的g值加上该节点对应的小轨迹的代价值。然后判断该节点是否在待拓展的开集合中,若不在,则将其加入到开集合中,记录该节点的g值以及父节点,并计算该节点的f值,该节点的评估结束,若已经在开集合中了,则判断该节点上面算出的新g值是否大于原有的g值,若是则不需要进行处理(该节点原有的方案更优),继续评估下一个节点,若不是,则说明该节点的现有方案更优,将该节点的父节点更新为 n c n_c nc,g值更新为新的g值,并更新计算该节点的总代价f值。本节点评估结束,继续评估下一个节点。

在这里插入图片描述


   下面来详细看一下上面流程中的一些具体细节:

   【注:Hybrid A * 算法每个具体执行过程的实现都有很多种方法,在前面的文章中,我们给出了 zhm_real/MotionPlanning运动规划库中的实现方法及细节,这里给出Fast Planner中的具体实现细节】

   (1)、如何由节点 n c n_c nc拓展生成小轨迹primitive——对应Expend函数

   将x,y、z轴的轨迹用三个独立的多项式来表示,比如用二次多项式 p x ( t ) = a 0 + a 1 t + a 2 t 2 p_x(t)=a_0+a_1t+a_2t^2 px(t)=a0+a1t+a2t2,自变量是时间t,则状态量和控制输入量可表示成以下的形式

   x ( t ) : = [ p ( t ) T , p ˙ ( t ) T , . . . , p ( n − 1 ) ( t ) T ] T ⊂ R 3 n u ( t ) : = p ( n ) ( t ) ∈ U : = [ − u m a x , u m a x ] 3 ⊂ R 3 \begin{aligned}&\mathbf{x}(t):=\boxed{\left[\mathbf{p}(t)^{\mathrm{T}}, \mathbf{\dot p}(t)^{\mathrm{T}},...,\mathbf{p}^{(n-1)}(t)^{\mathrm{T}}\right]^{\mathrm{T}}}\subset\mathbb{R}^{3n}\\&\mathbf{u}(t):=\mathbf{p}^{(n)}(t)\in\mathcal{U}:=[-u_{max},u_{max}]^3\subset\mathbb{R}^3\end{aligned} x(t):=[p(t)T,p˙(t)T,...,p(n1)(t)T]TR3nu(t):=p(n)(t)U:=[umax,umax]3R3

   然后,我们就可以写出状态空间方程,

   x ˙ = A x + B u A = [ 0 I 3 0 ⋯ 0 0 0 I 3 ⋯ 0 ⋮ ⋮ ⋮ ⋱ ⋮ 0 ⋯ ⋯ 0 I 3 0 ⋯ ⋯ 0 0 ] , B = [ 0 0 ⋮ 0 I 3 ] \begin{gathered}\dot{\mathbf{x}}=\mathbf{A}\mathbf{x}+\mathbf{B}\mathbf{u}\\\mathbf{A}=\begin{bmatrix}0&\mathbf{I}_3&\mathbf{0}&\cdots&\mathbf{0}\\\mathbf{0}&\mathbf{0}&\mathbf{I}_3&\cdots&\mathbf{0}\\\varvdots&\varvdots&\varvdots&\ddots&\varvdots\\\mathbf{0}&\cdots&\cdots&\mathbf{0}&\mathbf{I}_3\\\mathbf{0}&\cdots&\cdots&\mathbf{0}&\mathbf{0}\end{bmatrix},\mathbf{B}=\begin{bmatrix}\mathbf{0}\\\mathbf{0}\\\varvdots\\\mathbf{0}\\\mathbf{I}_3\end{bmatrix}\end{gathered} x˙=Ax+BuA= 0000I300I30000I30 ,B= 000I3

   这样,我们给定一个初始状态和一段时间内的控制输入里以后,就可以利用下式计算整条小轨迹上任意时刻的状态

   x ( t ) = e A t x ( 0 ) + ∫ 0 t e A ( t − τ ) B u ( τ ) d τ initial state control input \begin{aligned}\mathbf{x}(t)=e^{\mathbf{A}t}&\color{red}{\boxed{\mathbf{x}(0)}}+\color{black}\int_0^te^{\mathbf{A}(t-\tau)}\mathbf{B}&\color{red}{\boxed{\mathbf{u}(\tau)}}\color{black} d\tau\\&\color{red}{\text{initial state}}&\color{red}{\text{control input}}\end{aligned} x(t)=eAtx(0)+0teA(tτ)Binitial stateu(τ)dτcontrol input

在这里插入图片描述

   实际使用时,会对控制量在上下界范围内进行平均的离散采样,得到多组控制输入量,从而得到多条小轨迹

在这里插入图片描述

   在Fast-Planner中,n取值为2,即状态选取为位置和速度,输入为加速度

在这里插入图片描述


   (2)、如何计算每段小轨迹的代价值——对应EdgeCost函数

   对于一条小轨迹,在Fast-Planner中我们比较在意的是这条轨迹的执行时间和控制量,所以定义如下的代价函数(不同的需求和实际应用场景,可以选择不同的代价函数)

   T ( T ) = ∫ 0 T ∥ u ( t ) ∥ 2 d t + ρ T T(T)=\int_{0}^{T}\|\mathbf{u}(t)\|^{2}dt+\rho T T(T)=0Tu(t)2dt+ρT

   其中 T T T表示这一段小轨迹的时间, u u u是控制量, ρ \rho ρ表示对时间惩罚项的权重参数,对于一条小轨迹而言,在0~T时间内它的控制输入是固定的常量,每条小轨迹的总时间T也是固定的, 所以,我们并不需要计算上面的积分,它等效于使用下式来计算小轨迹的代价值, τ \tau τ即为小轨迹的持续时间

   e c = ( ∥ u d ∥ 2 + ρ ) τ e_{c}=(\|\mathbf{u}_{d}\|^{2}+\rho)\tau ec=(ud2+ρ)τ

   然后,我们把从起点开始的到当前节点的所有小轨迹的代价加起来,就得到了,从起点到当前节点的代价值,也就是该节点的g值,如下所示:

   g c = ∑ j = 1 J ( ∥ ( u d ) j ∥ 2 + ρ ) τ g_c=\sum_{j=1}^J\left(\left\|(\mathbf{u}_d)_j\right\|^2+\rho\right)\tau gc=j=1J((ud)j2+ρ)τ

在这里插入图片描述

   (3)、如何评估一个节点的启发代价值——对应Heuristic函数

   基于庞特里亚金最小原理设计了一条三阶的多项式轨迹,从当前状态出发,终止于目标点,轨迹的总时长已知,给定当前点和目标点的位置和速度,如下所示:

   p ( t ) = a 3 t 3 + a 2 t 2 + a 1 t + a 0 p ( 0 ) = p μ c , p ( 0 ˙ ) = v μ c p ( T ) = p μ g , p ( T ˙ ) = v μ g \begin{aligned}p(t)&=a_3t^3+a_2t^2+a_1t+a_0\\p(0)&=p_{\mu c},\quad p(\dot{0})=v_{\mu c}\\p(T)&=p_{\mu g},\quad p(\dot{T})=v_{\mu g}\end{aligned} p(t)p(0)p(T)=a3t3+a2t2+a1t+a0=pμc,p(0˙)=vμc=pμg,p(T˙)=vμg

   因此,可以得到该多项式系数满足下式:

   [ 0 0 0 1 0 0 1 0 T 3 T 2 T 1 3 T 2 2 T 1 0 ] [ a 3 a 2 a 1 a 0 ] = [ p μ c v μ c p μ g v μ g ] \begin{bmatrix}0&0&0&1\\0&0&1&0\\T^3&T^2&T&1\\3T^2&2T&1&0\end{bmatrix}\begin{bmatrix}a_3\\a_2\\a_1\\a_0\end{bmatrix}=\begin{bmatrix}p_{\mu c}\\v_{\mu c}\\p_{\mu g}\\v_{\mu g}\end{bmatrix} 00T33T200T22T01T11010 a3a2a1a0 = pμcvμcpμgvμg

   然后,基于庞特里亚金最小原理,得到最优的轨迹表达式如下:

   p μ ∗ ( t ) = 1 6 α μ t 3 + 1 2 β μ t 2 + v μ c t + p μ c [ α μ β μ ] = 1 T 3 [ − 12 6 T 6 T − 2 T 2 ] [ p μ g − p μ c − v μ c T v μ g − v μ c ] \begin{aligned}p_\mu^*(t)&=\frac{1}{6}\alpha_\mu t^3+\frac{1}{2}\beta_\mu t^2+v_{\mu c}t+p_{\mu c}\\\\\begin{bmatrix}\alpha_\mu\\\beta_\mu\end{bmatrix}&=\frac{1}{T^3}\begin{bmatrix}-12&6T\\6T&-2T^2\end{bmatrix}\begin{bmatrix}p_{\mu g}-p_{\mu c}-v_{\mu c}T\\v_{\mu g}-v_{\mu c}\end{bmatrix}\end{aligned} pμ(t)[αμβμ]=61αμt3+21βμt2+vμct+pμc=T31[126T6T2T2][pμgpμcvμcTvμgvμc]

   得到上面的位置轨迹后,求两阶导数可以得到加速度轨迹,在取位置和速度为状态量时,加速度也即控制输入:

   a μ ∗ ( t ) = α μ t + β μ u ( t ) : = [ a x ( t ) , a y ( t ) , a z ( t ) ] T \begin{aligned}&a_\mu^*(t)=\alpha_\mu t+\beta_\mu\\\\&\mathbf{u}(t):=[a_x(t),a_y(t),a_z(t)]^\mathrm{T}\end{aligned} aμ(t)=αμt+βμu(t):=[ax(t),ay(t),az(t)]T

   得到了这样一条轨迹后,就可以利用上面介绍的求小轨迹的代价的方式,求出这条轨迹的代价,作为考虑运动学但不考虑障碍物的启发式代价函数。

   T ∗ ( T ) = ∫ 0 l ∥ u ( t ) ∥ 2 d t + ρ T = ∑ μ ∈ { x , y , z } ( 1 3 α μ 2 T 3 + 1 2 α μ β μ T 2 + β μ 2 T ) + ρ T \begin{aligned} \mathcal{T}^{*}(T)& =\int_{0}^{l}\|\mathbf{u}(t)\|^{2}dt+\rho T \\ &=\sum_{\mu\in\{x,y,z\}}\left(\frac{1}{3}{\alpha_{\mu}}^{2}T^{3}+\frac{1}{2}\alpha_{\mu}\beta_{\mu}T^{2}+{\beta_{\mu}}^{2}T\right)+\rho T \end{aligned} T(T)=0lu(t)2dt+ρT=μ{x,y,z}(31αμ2T3+21αμβμT2+βμ2T)+ρT

   上面,我们假设时间T是人为给定的、已知的,但是很明显,我们并不清楚,从当前点到目标点合适的T应该如何选择。所以,我们可以将上式对T进行求导等于0,即 ∂ T ∗ ( T ) ∂ T = 0 \frac{\partial\mathcal{T}^*(T)}{\partial T}=0 TT(T)=0,来求取最合适的 T h T_h Th,进而得到代价值

在这里插入图片描述



   参考资料:

   1、[深蓝学院—移动机器人运动规划]

   链接放不了了,感兴趣的小伙伴自行查找吧

在这里插入图片描述


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1939611.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Haproxy服务

目录 一.haproxy介绍 1.主要特点和功能 2.haproxy 调度算法 3.haproxy 与nginx 和lvs的区别 二.安装 haproxy 服务 1. yum安装 2.第三方rpm 安装 3.编译安装haproxy 三.配置文件详解 1.官方地址配置文件官方帮助文档 2.HAProxy 的配置文件haproxy.cfg由两大部分组成&…

React+TypeScript 组件库开发全攻略:集成Storybook可视化与Jest测试,一键发布至npm

平时我除了业务需求,偶尔会投入到UI组件的开发中,大多数时候只会负责自己业务场景相关或者一小部分公共组件,极少有从创建项目、集成可视化、测试到发布的整个过程的操作,这篇文章就是记录组件开发全流程,UI组件在此仅…

RabbitMQ学习实践二:MQ的实现

文章是本人在学习springboot实现消息队列功能时所经历的过程的记录,仅供参考,如有侵权请随时指出。 参考文章地址: RabbitMQ安装与入门_rabbitmq win11配置-CSDN博客 RabbitMQ入门到实战一篇文章就够了-CSDN博客 RabbitMQ系列&#xff08…

AI跟踪报道第48期-新加坡内哥谈技术-本周AI新闻:Open AI 和 Mistral的小型模型

每周跟踪AI热点新闻动向和震撼发展 想要探索生成式人工智能的前沿进展吗?订阅我们的简报,深入解析最新的技术突破、实际应用案例和未来的趋势。与全球数同行一同,从行业内部的深度分析和实用指南中受益。不要错过这个机会,成为AI领…

华为路由器SSH登录实验

概念 SSH全称安全外壳(Secure Shell)协议,这个协议的目的就是为了取代缺乏机密性保障的远程管理协议,SSH基于TCP协议的加密通道,让客户端使用服务器的RSA公钥来验证SSHv2服务器的身份。 创建密钥对 在充当SSH服务器的…

UE4-获得角色控制权的两种方法

方法一: 方法二: 注意此方法不能有多个玩家出生点,如果有多个玩家出生点,会随机的选择一个玩家出生点进行生成。

C++的map和set介绍

系列文章目录 二叉树搜索树 map和set习题 文章目录 系列文章目录前言一、关联式容器键值对二、树形结构的关联式容器2.1 set2.1.1 set的介绍2.1.3 set的使用删除节点find的不同效率count举例lower_bound 和 upper_bound 2.2 multiset2.2.1 区别:find查找erase删除e…

Deepin系统,中盛科技温湿度模块读温度纯c程序(备份)

#include <stdio.h> #include <fcntl.h> #include <unistd.h> #include <termios.h>int main() {int fd;struct termios options;// 打开串口设备fd open("/dev/ttyMP0", O_RDWR | O_NOCTTY|O_NDELAY); //O_NDELAY:打开设备不阻塞//O_NOCTT…

http请求网址或网页的全流程

客户端通过浏览器请求网址或网页资源的步骤如下&#xff1a; http请求网址或网页的全流程 1.首先&#xff0c;浏览器做的第一步就是解析 URL 得到里面的参数2.浏览器封装 HTTP 请求报文3.DNS 域名解析获取 IP 地址4. 建立 TCP 连接5.浏览器发送请求6.负责传输的 IP 协议7.使用 …

基于Llama Index构建RAG应用(Datawhale AI 夏令营)

前言 Hello&#xff0c;大家好&#xff0c;我是GISer Liu&#x1f601;&#xff0c;一名热爱AI技术的GIS开发者&#xff0c;本文参与活动是2024 DataWhale AI夏令营&#xff1b;&#x1f632; 在本文中作者将通过&#xff1a; Gradio、Streamlit和LlamaIndex介绍 LlamaIndex 构…

【初阶数据结构】5.栈和队列

文章目录 1.栈1.1 概念与结构1.2 栈的实现2.队列2.1 概念与结构2.2 队列的实现3.栈和队列算法题3.1 有效的括号3.2 用队列实现栈3.3 用栈实现队列3.4 设计循环队列 1.栈 1.1 概念与结构 栈&#xff1a;一种特殊的线性表&#xff0c;其只允许在固定的一端进行插入和删除元素操…

从零开始实现大语言模型(八):Layer Normalization

1. 前言 Layer Normalization是深度学习实践中已经被证明非常有效的一种解决梯度消失或梯度爆炸问题,以提升神经网络训练效率及稳定性的方法。OpenAI的GPT系列大语言模型使用Layer Normalization对多头注意力模块,前馈神经网络模块以及最后的输出层的输入张量做变换,使shap…

android13 默认输入法配置分析rom默认配置修改分析

总纲 android13 rom 开发总纲说明 目录 1.前言 2.解决方法 3.方法分析 3.1方法1 3.2方法2 4.彩蛋 1.前言 Android13上需要预装中文输入法, 但是直接预装输入法的话,会出现默认使能的问题,点击TextEdit输入框, 弹出的是默认英文输入法LatinIME, 而不是谷歌拼音输入…

解决GoLand添加GOROOT提示The selected directory is not a valid home for Go Sdk的问题

现象 解决 在Go安装路径下找到zversion.go文件&#xff0c;我的在D:\Program Files\Go1.21.1\src\runtime\internal\sys下面 打开文件&#xff0c;添加如下内容&#xff1a; const TheVersion go1.21.1保存后再重新添加GOROOT即可

2024 杭电多校第一场

目录 目录 树 博弈 传送 树 给一棵根为 1 的有根树&#xff0c;点 i 具有一个权值 Ai 。 定义一个点对的值 f(u,v)max(Au,Av)|Au−Av| 。 你需要对于每个节点 i &#xff0c;计算 ansi∑u∈subtree(i),v∈subtree(i)f(u,v) &#xff0c;其中 subtree(i) 表示 i 的子树。 请…

如何让LabVIEW程序框图的图标简化,从而节省空间?

再点击选项 取消掉箭头所示的√即可。 这样就可以将生成的图标从下面所示&#xff1a; 变成简化的图标&#xff0c;如下所示&#xff1a;

UML的六大关系---泛化、实现、关联、聚合、组合、依赖

文章目录 前言1. 泛化关系(Generalization)2. 实现关系(Realization)3. ‌关联关系(Association)4. 聚合关系(Aggregation)5. 组合关系(Composition)6. 依赖关系(Dependency)总结 前言 讲到设计模式&#xff0c;就会有 U M L UML UML类图这个东西。 一开始就很难理解各种线啥意…

【Spring Boot】网页五子棋项目中遇到的困难及解决方法

目录 一、HikariPool-1 - Starting异常二、Invalid bound statement (not found)异常三、The driver is automatically registered via the SPI and manual loading of the driver class is generally unnecessary异常四、The server time zone value时区报错异常五、补充知识点…

CSS技巧专栏:一日一例 6 - 纯CSS实现粉红色跳出来的立体按钮特效

纯CSS实现粉红色跳出来的立体按钮特效 今天要介绍的案例,是个相对简单的按钮效果,我们先看图: 案例分析 我说它简单,因为它实际上并没有使用什么特别的动画效果,只是几个简单的动画组合: 利用伪类before和after,制作按钮后面两个透明的粉色填充层,左右移动。给文字层…

代码随想录算法训练营第23天|39. 组合总和、40.组合总和II、131.分割回文串

打卡Day23 1.39. 组合总和2.40.组合总和II3.131.分割回文串 1.39. 组合总和 题目链接&#xff1a;39. 组合总和 文档讲解&#xff1a; 代码随想录 这道题和昨天做的组合之和由两个区别&#xff1a;被选的元素没有数量限制&#xff0c;同时被选的元素可以无限重复&#xff0c;…