运动规划入门 | 1. 白话Dijkstra,从原理到Matlab实现

3870
137
2020年3月27日 14时09分

在运动规划的研究场景里很多已经存在的经典算法,在运动规划的入门阶段绕不过去的五种基础算法分别有:DijkstraAstar(A*)PRM(概率路线图法Probabilistic Road Maps)RRT(重复探索随机树 Rapidly Exploring Random Trees)人工势场法(Artificial Potential Fields)

 

笔者将会更新这个“运动规划入门”系列,尽我所能详细地给小伙伴们分别讲解这五种算法。由于笔者能力有限,讲解内容有任何错误的话,请务必指正。

 

Dijkstra与“图(Graph)”不得不说的那些事

 

“图”是一种用于描述对象和对象之间的数学方法。如下图所示,这是一个具有7个节点(node)的无向图,节点和节点之间的连线称为边(edge),每条边都具备一定的权重(weight),“图”在运动规划中是一个十分重要的数学工具。

 

1

 

由于这样子更加直观,所以通常我们都会使用图来讲解Dijkstra的算法原理。从贴合直觉的角度来描述图的话,举个例子:A,B,C,D,E,F,G分别是7个城镇,城镇和城镇之间有些铺设了高速公路,有些则没有,这就是“边”。假设我们现在要找出从城镇A到城镇G之间路程最短的路线,而每段高速公路的路程都可能不一样,那么我们就把路程看为权重或者说是代价(cost),很明显我们就是要找出一条总代价(总权重)最小的路线。再假设,我们现在不想找最短路线了,我想找最经济的路线(路费最低),那么我们就会将费用视为代价,并尝试找出总代价最低的路线。

Dijkstra基本原理图解

ok,我们就用下面这个图来距离Dijkstra算法,假设起点是A,终点是G,每条边具备不同的代价值,我们的任务就是找出从A到G代价最小的路径。每个节点还具备两个属性值,一个是node_cost,这个node_cost记录了当前节点到起点的已知的最小总代价值,这个node_cost会在算法迭代过程中由于规划出来的路径不相同而被更新成不同的值。另一个属性值是parent,parent表明了根据当下规划出来的路径,该节点对应的父节点,比如说:节点F的父节点可能是B也可能是D也可能是E,在完全取决于我们选择哪条路径。

 

在示意图中圆圈中的“C,1,A”表示:该节点是C,按照当前规划的路径,C节点的父节点是A,且C节点到起点的代价值为1。

 

2

 

为了方便起见,我们用绿色代表起点,黄色代表终点,红色代表该点已经完成遍历,蓝色节点表明该节点尚未完成遍历。白色代表尚未纳入考虑范围之内。在Dijkstra算法开始之前,我们将起点的node_cost设为0,其余节点的node_cost设为无穷(infinite),所有节点的parent均设置为空。未完成列表里只有起点。已完成列表为空。

 

Dijkstra是一个迭代的过程,在每轮迭代的开始,我们会找出未完成遍历列表中的所有节点中node_cost最小的那个节点并设置为current_node,并将这个被选中的current_node移除未完成列表,设置为已完成遍历。每轮迭代中,我们都会对current_node的所有未完成遍历的相邻节点进行单独的判定,判定相邻节点当前的node_cost是否大于current_node的node_cost与连接边的代价值之和。如果大于的话,将相邻节点的node_cost更新为current_node的node_cost加上连接边的代价值,并且将相邻节点的parent更新为current_node,如果这个相邻节点尚未被加入未完成列表,则将其添加进列表中。如果小于的话,则保持原样,不执行任何操作。

 

举个例子:在第一轮迭代开始时,由于A是node_cost最小的节点,所以A被设置为current_node,并被标记为已完成遍历,接着我们会从A开始进行第一轮搜索,我们可以看到与A相邻的节点分别有B,C,D。对于A的相邻节点B来说,当前B的node_cost = inf,A的node_cost = 0,连接边的cost = 2。很明显B.node_cost > A.node_cost + edge.cost,那么我们就将B的node_cost更新为2,B的parent更新为A。同样的道理,对其余两个相邻节点进行判定。结果如下图所示。

 

3

 

那么第二轮迭代我们在未完成列表中寻找具备最小node_cost的节点,很明显最小的是节点C,将C移出未完成列表后,我们就对C的相邻节点进行单独判定。完成判定后结果如下:

4

 

以此类推,第三轮迭代我们选择B为current_node,则的结果为:

 

5

 

第三轮迭代我们选择D为current_node,则的结果如下,我们注意到了F的node_cost被更新为3,这就意味着找到了一条从起点A到达F花费代价更低的路径,这便是Dijkstra算法的精髓所在——每次迭代都在产生规划出代价更低的路径。你品,你细品。

 

6

 

第四次迭代中,我们毫无悬念地选择了E作为current_node,我们发现G是E的相邻节点,那么恭喜,我们成功找到了A到G的路径。但是有个问题值得思考:Dijkstra找到的最短路径是唯一的吗?

 

7

 

当我们完成规划以后该如何根据规划结果找到那条最短路径呢?这时我们之前一直没有发挥作用的属性值parent就要大显神威了,这一招有点像我们成语讲的“顺藤摸瓜”,我们从终点开始,根据当前节点的parent值一个一个往回走就能回到起点了。这也就把路径描绘出来了。

 

8

 

Dijkstra的matlab实现

地图表示法:网络占用法

表示地图以及机器人在地图中的位置的方式有很多种,比如可以把地图表示在笛卡尔坐标系中,比如一个二维的地图:坐标[x, y]表明机器人在地图中的位置,地图中的机器人本体和障碍物分别用一个个多边形表示。这种表示方式的优点就是简单,我们可以只使用很少的信息就能表达出一张完备的地图。但是优点明显的同时,其缺点也很明显。假设我们要对机器人和障碍物之间进行碰撞检测,那么我们需要将代表机器人和障碍物的多边形进行判定,判定其是否产生重叠。实际上我们在实际操作时往往将多边形视为由多个三角形组成,因为三角形和三角形之间的重叠检测比较容易。但是这种检测方式要求对三角形的每条边都进行计算测试,如果是一张小地图的话那么计算压力还不算太大,但是如果地图稍微大一点,或者障碍物稍微多一点的话,那么这种地图表示法所需的计算成本就会大幅度上升。

 

所以在此,我们选择另一种地图表示法:网络占用法。这种方法会将整个地图区域分割为若干个单位网络栅格,每个栅格的最基本状态有非占用(free space)和占用(obstacle)。

 

非占用栅格,即机器人可以自由通过的栅格,比如下图中的白色栅格。占用栅格也就是机器人无法通过的栅格,即障碍物,比如下图中的黑色栅格。单位网络栅格的大小决定了地图的分辨率,单元格的大小往往根据应用场景的不同设置为不同的数值。当区域扩大或者单元格缩小时,地图所需的存储空间就会增大。但是对于现代计算机的硬件水平而言,这种方法是非常可行的。

 

按照惯例我们需要做一些必要的假设:机器人在地图网络中活动,且只占用一格的空间。机器人可以移动到任意相邻非占用栅格。

 

9

 

地图生成

前面说网络占用法的时候老是栅格来栅格去的,那么我们究竟该如何在matlab中表示一张占用网络地图呢?其实说破不值一毛钱,在matlab中一个二维的占用网络地图就是一个二维的矩阵,如下图所示:在这张地图中,我们用0来表示非占用栅格,1表示占用栅格

 

10

 

Robotic Tool Box(后文简称RTB)里有专门的函数可以帮助我们生成一张地图,毕竟如果要你手动来一个个栅格单独配置的话实在是太麻烦了。

 

RTB里构建地图的函数为makemap(),比如我们生成一个20*20的地图,我们可以使用命令makemap(20),执行命令后将会弹出一个网络图,以及帮助信息。

 

11

 

可以看到它的帮助信息十分的简单明确,你可以用鼠标左键在网络图中点击或者拖动来创建图案,或者选择figure窗口并在键盘上输入快捷命令来生成多边形或者圆形等等。

 

12

 

比如我在这画了一个圆(分辨率比较低。。。)

 

13

 

然后回车,就能得到生成好的map了,是不是巨方便

 

14

 

最后将生成的map保存下来,就能在自己的代码中重复使用这个地图了。

Dijkstra算法流程

15

 

在代码实现中,NodeCostList除了记录总代价值之外同时兼备未完成列表的功能,每轮迭代中,我们在获得一个新的current_node之后,便会马上将current_node的NodeCost设置为Inf,确保在下一轮迭代中,由于Inf比任何值都大,所以只要NodeCostList至少出现一个非Inf的值,那么这个节点不会被再次选中。

 

在流程图中未出现的变量是我们的占用地图map,在实际代码中,map的栅格属性不单单只有占用和非占用两者,为了演示和实现的便利,我们一共引入了7种状态值,分别是非占用、占用、起点、终点、已完成遍历、未完成遍历以及路径(路径状态只有在完成Dijkstra算法后才被赋予)

 

16

 

核心代码

这部分就没什么好讲的了,直接放代码吧,需要完整matlab源码的小伙伴可以在评论区找我要蛤~

 

while true
	[min_node_cost, current_node_index] = min(node_cost_list(:));
	if(min_node_cost == inf || current_node_index == destination_index)
		plan_succeeded = true;
		break;
    end
    node_cost_list(current_node_index) = inf;
    map(current_node_index) = Finished;
	[x,y] = ind2sub(MapSize, current_node_index);
    for k = 0:3	% four direction
		if(k == 0)
		    adjacent_node = [x-1,y];
		elseif (k == 1)
			adjacent_node = [x+1,y];
		elseif (k == 2)
			adjacent_node = [x,y-1];
		elseif(k == 3)
			adjacent_node = [x,y+1];
		end
		
		if((adjacent_node(1) > 0 && adjacent_node(1) <= MapSize(1)) && (adjacent_node(2) > 0 && adjacent_node(2) <= MapSize(2))) % make sure the adjacent_node don't exceeds the map
            if(map(adjacent_node(1),adjacent_node(2)) ~= Obstacle && map(adjacent_node(1),adjacent_node(2)) ~= Finished)
                if(node_cost_list(adjacent_node(1),adjacent_node(2)) > min_node_cost + 1)
                    node_cost_list(adjacent_node(1),adjacent_node(2)) = min_node_cost + 1;
                    if(map(adjacent_node(1),adjacent_node(2)) == Origin)
                        parent_list(adjacent_node(1),adjacent_node(2)) = 0;	% Set the parent 0 if adjacent_node is the origin.
                    else
                        parent_list(adjacent_node(1),adjacent_node(2)) = current_node_index; % Set the parent current_node_index
                    end
                    map(adjacent_node(1),adjacent_node(2)) = Unfinished; % Mark the adjacent_node as unfinished
                end
            end
        end
	end
end

 

最终的演示效果,可以看到方块就像洪水一样向四周扩散,直到找到终点为止。当然如果当前的规划问题是无解的话Dijkstra也会返回错误警告(或者空结果)。

 

Dstar_animation

 

Dijkstra的优缺点

Dijkstra的优点我觉得其实就是算法简单,像洪水一样向四周无脑扩散就完事儿了。在上面的演示中其实看起来效果还是不错的,但是请注意,这只是一张20*20的地图而已,那么假如我们把地图扩大到100*100的时候会是什么效果呢?

 

是这样的:。。。。

 

Dstar_animation_2

 

是不是你都没耐心看下去了,我都没耐心录完全程。所以一旦地图扩大,Dijkstra的无脑扩散就显得力不从心了。下一篇笔者将为你解说A*是如何解决这个问题的。

发表评论

后才能评论

评论列表(137条)

  • 启越 2020年10月14日 上午7:03

    写得很好!谢谢博主!能发一份源码供学习吗?谢谢!我的邮箱:1796483016@qq.com

    • tloinny 回复 启越 2020年10月16日 上午11:21

      邮件已发,注意查收,祝您生活愉快!

  • Oscar 2020年10月13日 下午8:26

    老师,我刚忘记发邮箱了,补充下邮箱:18249516788@163.com

  • Oscar 2020年10月13日 下午8:25

    老师,您好!我最近在学习Motion Planning,请问可以发一份源代码吗?万分感谢您!

  • 7djip_6698 2020年10月13日 下午5:18

    老师 能发一份源码吗?邮箱:875193130@qq.com 感谢!

  • xqyvc_2188 2020年10月13日 下午2:00

    老师您好,我最近在做关于机器人路径规划,请问可以发一份源代码做参考么?15385442188@163.com, 谢谢!

    • tloinny 回复 xqyvc_2188 2020年10月16日 上午11:20

      邮件已发,注意查收,祝您生活愉快!

  • jgmm0_4319 2020年10月10日 下午9:45

    老师您好!
    我有个问题不是很明白,想请教一下您
    您上面的流程图那里,不清楚为什么将currentnode_nodeCost的值赋为inf,是否是为了防止在迭代中parent节点再次被选中?但是如果赋值inf不就和其他正常被赋予inf的节点一样了吗?如何能做到不被再次选中呢?

    • tloinny 回复 jgmm0_4319 2020年10月11日 上午10:23

      每轮迭代的开头[min_node_cost, current_node_index] = min(node_cost_list(:));这一句就是在选出list中代价值最小的节点。只要迭代尚未结束,node_cost_list中必然存在比inf小的数,所以已经被设置为inf的节点不会被再次选中。

    • jgmm0_4319 回复 tloinny 2020年10月11日 下午12:55

      是说在将红色节点赋值为无穷大之前,蓝色节点就已经从inf变为各自的cost值了?但从流程图上看总觉得是先给红色节点赋值inf后再进行比大小、赋值操作的,那红色节点的值已经从原本cost改为inf了,如何进行后续的求和呢?

  • 躲藏悲伤的风 2020年10月9日 下午2:48

    老师,您好,可以发一份源代码么?十分感谢 邮箱:949043391@qq.com

  • kumzy_9571 2020年10月6日 下午5:09

    老师,麻烦您发一下源代码,万分感谢!2316011738@qq.com

  • kumzy_9571 2020年10月5日 下午5:16

    老师可以发一份源码吗?万分感谢! 邮箱:2316011738@qq.com

  • 0d4e3_6404 2020年9月28日 下午7:47

    老师您好,可以发一份地图源码吗?十分感谢 邮箱:158321223@qq.com

  • Sangdada 2020年9月18日 下午4:35

    老师,可以发一份源码吗?十分感谢 邮箱:1412178919@qq.com

    • tloinny 回复 Sangdada 2020年9月18日 下午7:49

      邮件已发,注意查收,祝您生活愉快!

  • p6klk_3778 2020年9月16日 下午9:19

    老师,麻烦您发一下源代码,从第一课开始学 matthew_sjtu@163.com

  • szgkw_9785 2020年9月16日 下午8:38

    老师麻烦发一下源代码,谢谢!!1581844212@qq.com

    • tloinny 回复 szgkw_9785 2020年9月16日 下午11:23

      邮件已发,注意查收,祝您生活愉快!

  • 灬ぺо僤蒓 2020年9月16日 下午7:27

    老师,可以发一份源码吗?十分感谢 邮箱:634898201@qq.com

  • u5kg9_9327 2020年9月16日 下午4:31

    老师您好,希望老师讲的轨迹规划的系列的代码发一份,十分感谢! 谢谢!目前正在学习中 邮箱:924832937@qq.com

    • tloinny 回复 u5kg9_9327 2020年9月16日 下午11:22

      邮件已发,注意查收,祝您生活愉快!

  • 2020年9月5日 下午9:34

    老师,可以发一份源码吗?十分感谢 邮箱:449656595qq.com

    • 回复 2020年9月5日 下午9:39

      已收到,谢谢老师!!!

    • tloinny 回复 2020年9月5日 下午9:39

      邮件已发,注意查收,祝您生活愉快!

  • vy59l_1269 2020年9月4日 下午12:47

    老师求源码啊 好人一生平安:707933073@qq.com

    • vy59l_1269 回复 vy59l_1269 2020年9月4日 下午12:48

      希望 老师讲的 轨迹规划的系列的代码 发一份啊 谢谢!学习中

    • tloinny 回复 vy59l_1269 2020年9月5日 下午9:38

      邮件已发,注意查收,祝您生活愉快!

  • 小熊Paddle 2020年9月1日 上午10:57

    老师,可以发一份源码吗?十分感谢 邮箱:32488484@qq.com

  • i1lpv_2442 2020年8月26日 下午3:23

    老师,可以发一份源码吗?十分感谢 邮箱:553185637@qq.com

  • ri41s_2870 2020年8月17日 下午2:40

    老师,可以发一份路径规划1-5的源码吗,非常感谢!937545848@qq.com

  • lqfnm_9115 2020年8月16日 上午11:37

    楼主 麻烦发一份路径规划入门系列1-5的完整运行代码,谢谢啦。chenwanli9999@163.com

    • tloinny 回复 lqfnm_9115 2020年8月16日 上午11:45

      邮件已发,注意查收,祝您生活愉快!

  • lqfnm_9115 2020年8月16日 上午11:30

    楼主 麻烦发一份Dijkstra和A*代码的完整运行代码,谢谢啦。chenwanli9999@163.com

  • okyu1_7501 2020年8月16日 上午6:33

    老师您好,我正在学习路径规划的算法,写代码当规模比较大的时候总是会遇到无法运行下去的问题。您能发一份Dijkstra和A*代码给我参考和学习吗?非常感谢!邮箱ielfshen@163.com

    • tloinny 回复 okyu1_7501 2020年8月16日 上午11:45

      邮件已发,注意查收,祝您生活愉快!

  • zhangss 2020年8月6日 下午3:10

    老师,您好,我正在学习路径规划算法,请问能发一份代码给我吗?十分感谢,邮箱:zhangss0817@outlook.com

    • tloinny 回复 zhangss 2020年8月6日 下午8:12

      邮件已发,注意查收,祝您生活愉快!

  • sid870727 2020年8月6日 上午1:04

    老师您好,能发一份Dijkstra和A*代码给我吗十分感谢。邮箱:sid870727@yahoo.com.tw

    • tloinny 回复 sid870727 2020年8月6日 上午9:40

      邮件已发,注意查收,祝您生活愉快!

  • 鸩罂粟 2020年7月28日 下午11:42

    老师,您好。最近刚重新学习路径规划内容,看了你的文章受益匪浅。希望能要一下这个“运动规划入门”系列的maltab代码学习,可以麻烦您抽空发我一份吗?谢谢。 邮箱:1239746476@qq.com

    • tloinny 回复 鸩罂粟 2020年7月29日 下午1:05

      邮件已发,注意查收,祝您生活愉快!

  • 无论你在哪我都会去找你 2020年7月24日 上午10:19

    老师,您好,可以发一份源码给我吗?想学习用,十分感谢。邮箱:xhma1998@163.com

  • 91q51_2196 2020年7月22日 下午3:16

    老师,可以发一份源码吗?十分感谢 邮箱:2664126847@qq.com

    • tloinny 回复 91q51_2196 2020年7月23日 上午12:25

      邮件已发,注意查收,祝您生活愉快!

  • amgl9_7813 2020年7月18日 下午4:15

    您好,正在学习,能发一份代码给我吗?十分感谢!hubert_hy@163.com

  • vxfo0_1261 2020年7月18日 下午3:46

    老师,您好,我正在学习路径规划算法,请问能发一份代码给我吗?十分感谢,邮箱:873508297@qq.com

  • 心雕 2020年7月18日 上午7:50

    老师好。感谢详细的讲解,可以发一份Dijkstra和A*代码给我继续学习吗,谢谢!190139630@qq.com

    • tloinny 回复 心雕 2020年7月18日 下午1:01

      邮件已发,注意查收,祝您生活愉快!

  • 十里村的放牛娃 2020年7月17日 上午10:14

    老师您好,感谢详细的讲解,有劳您发一份Dijkstra和A*代码继续学习,谢谢!993800153@qq.com

  • 荒废的记憶 2020年7月16日 下午11:10

    老师您好,求一份Dijkstra和A*代码,1666352346@qq.com,感谢!

  • yoicl_1380 2020年7月15日 下午11:12

    老师您好,求一份Dijkstra和A*代码,937093076@qq.com,感谢!

  • 折欲 2020年7月9日 下午5:49

    老师您好,感谢您的讲解,想要一份dijkstra和a*的代码深入学习,邮箱:1034525526@qq.com,万分感谢!

    • tloinny 回复 折欲 2020年7月12日 下午5:41

      邮件已发,注意查收,祝您生活愉快!

  • q3ggw_2595 2020年7月7日 下午3:34

    老师您好,我想要一份dijkstra和a*的代码,邮件:781434300@qq.com。谢谢您!

  • 197dp_5539 2020年6月23日 下午11:28

    老师您好,感谢您的讲解,想跟您要一下dijkstra和a*算法的代码,如果可以的话还想跟您要一份动画实现的代码@@。邮箱是:1017070223@qq.com,谢谢您了。

  • 弟弟 2020年6月18日 下午8:58

    老师您好,我想要一份dijkstra和a*的代码,邮件:420663409@qq.com。谢谢您!

    • tloinny 回复 弟弟 2020年6月18日 下午11:18

      邮件已发,注意查收,祝您生活愉快!

  • Never Settle 2020年6月15日 下午10:17

    老师您好,求一份dijkstra和a*的代码,邮箱:1273547688@qq.com。谢谢您!

  • lvk4u_5330 2020年6月11日 下午2:51

    老师,您好,求一份dijkstra的代码,谢谢!
    邮箱:1181167305@qq.com

    • tloinny 回复 lvk4u_5330 2020年6月12日 下午11:13

      邮件已发,注意查收,祝您生活愉快!

  • 一见天 2020年6月9日 下午9:19

    老师,您好,求一份dijkstra的代码,谢谢
    邮箱:541034902@qq.com

  • 1nuu9_0172 2020年6月1日 下午9:14

    老师,您好,求一份dijkstra的代码,谢谢您!
    邮箱:2214651958@qq.com

  • 彼此错过的那些年 2020年6月1日 下午3:23

    老师您好,求一份源代码,邮箱908526512@qq.com

  • 1aqdi_8337 2020年5月31日 下午10:42

    老师您好,求一份dijkstra和a*的代码,邮箱:3023259638@qq.com。谢谢您!

  • gytvo_0089 2020年5月18日 下午11:20

    老师好!求一份源码学习,1269185184@qq.com,谢谢!

  • 断剑残血 2020年5月16日 下午8:00

    makemap()函数要怎么用呢 为什么我添加了 Robotics Toolbox工具箱后,在命令行输入map=makemap(20),却提示:未定义函数或变量 ‘makemap’。?? 请您解答下,谢谢了

    • tloinny 回复 断剑残血 2020年5月17日 上午12:27

      首先确定您是否已经正确安装了RTB以及配置好了matlab的搜索路径,然后再确定您是否没有在matlab中启动RTB,可以在命令行中使用startup_rtb手动启动RTB。最后检查您的RTB版本,我个人使用的是matlab2017a,Robotics Toolbox for Matlab (release 9.10)。如果您使用的版本和我的差得比较远,那么可能存在函数名称不一致的情况,如果是这样的话那您只能找找看您用的版本是哪个函数了。

    • szgkw_9785 回复 tloinny 2020年9月17日 下午2:14

      matlab2018a,Robotics Toolbox for Matlab (release 10.2)还是报错,有其他的方法嘛,多谢

  • fnz9c_8193 2020年5月14日 下午5:09

    老师您好,求一份dijkstra和a*的代码,邮箱:617608566@qq.com。十分感谢!

  • 古尔丹是大反派 2020年5月13日 下午11:58

    老师您好,求一份dijkstra和A*算法的MATLAB代码,vtasyao@163.com

  • p2d72_2513 2020年5月13日 下午1:31

    老师好,求一份dijkstra和a*的代码,116631557@126.com

    • tloinny 回复 p2d72_2513 2020年5月14日 下午12:09

      邮件已发,注意查收,祝您生活愉快!

  • zqkqu_7991 2020年5月12日 下午9:48

    老师好,求一份dijkstra和a*的代码,邮箱:499281736@qq.com。非常感谢

    • tloinny 回复 zqkqu_7991 2020年5月12日 下午10:37

      邮件已发,注意查收,祝您生活愉快!

  • Rene 2020年5月12日 下午12:50

    老师您好,求一份a*和dijkstra的源代码,邮箱:1196461170@qq.com 非常感谢!

    • tloinny 回复 Rene 2020年5月12日 下午1:32

      邮件已发,注意查收,祝您生活愉快!

  • 麦田的守望 2020年5月6日 下午10:16

    博主可以发一份源码吗?想参考以下,非常感谢!

  • nuf4j_7912 2020年5月5日 下午8:29

    楼主,可以也发我一份代码学习下吗,非常感谢,谢谢 zengpiaoyang123@163.com

  • 渐行渐远 2020年5月3日 下午2:37

    可以发我一份代码吗?学习学习,非常感谢,sunjixing1996@163.com

  • h2cul_1935 2020年4月28日 下午11:26

    你好,有1个疑问:
    (1)你的详细步骤中,第三轮迭代后,F点处的值为何是(F,3,B)?不应该是(F,3,D)?
    然后,希望能进一步结合源码对该算法进行学习,185405890@qq.com,感谢!

    • tloinny 回复 h2cul_1935 2020年4月29日 下午12:41

      您说的没错,(F,3,D)是正确的,是我忘记修改图片中的字母了,感谢指正!!!

    • tloinny 回复 h2cul_1935 2020年4月29日 下午12:42

      邮件已发,注意查收,祝您生活愉快!

  • hello 2020年4月24日 下午12:53

    您好,写得太好了,希望能看源码学习下,526091944@qq.com,谢谢!

    • tloinny 回复 hello 2020年4月25日 下午1:14

      邮件已发,注意查收,祝您生活愉快!

  • o′sLovex 我、o 2020年4月24日 上午11:12

    请发我一份代码,感谢 462811380@qq.com

  • 05qmp_4270 2020年4月18日 下午8:06

    您好,我很有兴趣想学习一下,可以发我邮箱么,谢谢大佬~2403633845@qq.com

    • tloinny 回复 05qmp_4270 2020年4月19日 上午12:09

      邮件已发,注意查收,祝您生活愉快!

  • Willzoe 2020年4月15日 上午3:12

    您好 可以发我一份代码吗?谢谢~ 1710012427@qq.com

    • tloinny 回复 Willzoe 2020年4月15日 上午11:31

      邮件已发,注意查收,祝您生活愉快!

  • 求知者 2020年4月14日 上午10:35

    您好,您的帖子非常有用。期待您更新人工势场法

    • tloinny 回复 求知者 2020年4月15日 上午11:32

      谢谢,不过目前精力有限,只能当月更侠了

  • 符号看象限、 2020年4月13日 下午1:51

    请发我一份代码,感谢 310494553@qq.com

  • dtvee_6515 2020年4月12日 下午7:28

    多谢,麻烦也发我一份,690064483@qq.com

  • wk32m_8959 2020年4月11日 下午1:13

    您好,我想要一份代码,感谢~ 325179555@qq.com

  • zaasb_8261 2020年4月9日 下午8:58

    想要一份代码学习,,谢谢您

  • u3oey_0531 2020年4月8日 上午11:35

    请问这个移动机器人的运动规划吗? 感谢分享 yxwq6318@163.com

    • tloinny 回复 u3oey_0531 2020年4月8日 下午12:59

      本文只是对规划算法的讲解,以及matlab的演示。不一定非得限制在移动机器人的运动规划,假如将规划算法中的地图换成机械臂的cspase,那么也可以做机械臂的运动规划。

    • tloinny 回复 u3oey_0531 2020年4月8日 下午12:59

      邮件已发,注意查收,祝您生活愉快!

  • amoje_7679 2020年4月7日 下午10:20

    感谢博主源代码分享,邮箱 skp0933@outlook.com

  • nrpi6_7870 2020年4月7日 下午2:05

    感谢博主源代码分享,我的邮箱137558282@qq.com

  • 之易安 2020年3月31日 下午3:24

    求一份源码学习,1908209288@qq.com,谢谢!

    • tloinny 回复 之易安 2020年3月31日 下午3:44

      邮件已发,注意查收,祝您生活愉快!

  • 罗伯特祥 2020年3月29日 下午12:59

    跟大佬学习学习,我也讨一份代码,邮箱songhongxiang@163.com

  • shaw 2020年3月27日 下午8:35

    可以发下完整matlab源码我学习一下嘛?