数据结构之树与栈结合-启发式寻路

1. 实际距离(f) = 实际代价(g) + 预估代价(h)在这里插入图片描述

如图我们从起点到终点位置需要绕开障碍物,我们实际走的距离是称为实际代价, 而中间位置到达终点位置,我们的路线不确定, 所以算作预估代价。

2. 曼哈顿距离

在这里插入图片描述
图中的红色线 就是曼哈顿距离

做启发式寻路,就是从起点位置不停的找可以走的点, 然后计算实际代价和预估代价,所以预估代价需要不停的计算,这个计算的次数非常大,为了方便计算,所以预估代价我们用曼哈顿距离计算。

3. 启发式寻路的思想

第一步

在这里插入图片描述
如图 想从起点到达终点 怎样找到最进的位置, 我在在起点位置找到可以走的所有方格 ,计算它的实际代价(g)和预估代价(h),找到实际距离 (f) 最小的空格,显然50是最小的。 随机找一个50 空格填入黄色格子。

第二步

在这里插入图片描述
在已经选中的黄色格子中周围继续补上白色格子,计算他们对应的 g h 和f值,根据f最小原则, 找到第二个黄色格子 f=50。

第三步

在这里插入图片描述
给第二个黄色格子,周围的白色补上 g h f 值,然后在剩余的白色格子中找到一个 f最小的值的格子。找到依然是50

第四步

在这里插入图片描述
给第三个黄色格子填上周围填上 g h f 值,然后查看所有白色格子中, 最小f值的格子 显然是64。

第五步

在这里插入图片描述
同上,然后把找到的格子填上黄色,然后计算周围可用的白色格子,并填上 g h f 值, 依然找最小的f 依然是64

第六步

在这里插入图片描述
同上,然后把找到的格子填上黄色,然后计算周围可用的白色格子,并填上 g h f 值, 依然找最小的f 依然是64

第七步

在这里插入图片描述
给64 这个格子填上黄色,然后继续给周围可以用的白色格子,填上对应的 g h f 值,找都爱有值的白色格子的f值最小的格子 是 58这个格子

第八步

在这里插入图片描述
然后给58 这个格子填上黄色,然后继续给周围的白色格子 填上 g h f 值(漏了一个白色格子,不过不影响结果)。最终找到白色格子中值最小的是 终点格子 52。
至此 我们就寻找到了终点位置,那么如何确定路线呢?

4. 开放列表与关闭列表

上面我们分析了启发式寻路的思想,这种时候我们介绍两个概念, 关闭列表和开放列表。 上图中的开放列表 就是白色格子, 黄色格子就是关闭列表。 我们每次都在白色格子中找最小值,然后放到黄色格子, 然后在黄色格子周围开辟新的格子,添加到开放列表中, 然后继续找最小,依次类推。

PriorityQueue优先级队列 开放列表的数据可以使用优先级队列存储, 默认它会把最小值 元素放在最上面。

5. 模型建立

在这里插入图片描述
如图,我们可以给所有的格子编上号码,便于识别。根据上面的分析,我们可以根据 白色格子的数值的填充过程建一棵树; 比如
1、起点 14 生成了 8 9 13 18 19 这五个白格子;
2、找到一个最小的f距离 9 ,当然这里有三个最小,随机找的9 也可以是其他。 在9 周围生成3个格子
3、 然后另外最小的格子,13 生成 7 12 17 ;
4、剩下的最小格子就是19 , 在它周围生成了 21 22两个格子。
5、接下来最小值就是64 一次生成了 1 和 20 两个格子
6、接着剩下的最小格子,依然是64 编号是4,生成 5和10 两个白色格子 (注意:过程是根据代码逻辑,可能第一次就找到4 这个格子,然后第五步就可以省略 )
7、然后找到最小格子 10 生成了6 11 16 15 四个格子,并且终点是16.
根据上面的步骤,我们就生成了一棵树。并且找到了终点。 如何找到最短路径呢, 其实我们从终点开始循环遍历,找父节点,最终路径就是一条最短路径。
我们可以使用一个栈数据结构存储, 从终点节点向上找父节点,入栈,然后在找这个节点的父节点入栈。
在这里插入图片描述
最后从栈中取出 格子,就是我们需要走的最短路径: 14 -> 9 -> 4 -> 10 -> 16
博客图片资源

发布了58 篇原创文章 · 获赞 16 · 访问量 6万+

猜你喜欢

转载自blog.csdn.net/dingshuhong_/article/details/104457637