Android路径搜索算法

UDKOX

语境

我正在尝试开发一个简单的2D游戏,其中一些“僵尸”将追逐我。

我计算路径的想法如下(X =路径不可用):

[4] [4] [X] [1] [1] [2] [3] [4] [5]
[3] [X] [X] [0] [1] [X] [X] [X] [5]
[3] [2] [1] [1] [1] [X] [3] [4] [5]
[3] [2] [2] [2] [2] [2] [3] [4] [5]

从0开始,给它大约1的位置,给接近1的位置,给2的值,依此类推。这样,我只需要搜索一个较低的索引就可以知道达到0的最快方法。

问题

(1)我不知道此算法是否具有名称,因此我无法真正找到有关它的信息。

(2)计算此最优解/算法/流

(3)在我的手机中,游戏屏幕的分辨率为1700 x 1440,因此我的代码需要15秒。我创建了一个最终值来缩小和缩小矩阵的大小,但是,stil花费了很多,实际上是无法玩的。

(4)还有其他需求吗?也许添加线程?我不知道那是否行得通...

我的代码(调试代码已删除)

代码

private void expandAllFrom(int x, int y){ // x and y already scalled down
    nodes = new ArrayList<Point>(); // "nodes" is a global variable //
    nodes.add(new Point(x, y));

    while ( nodes.size() > 0 ){
        Point p = nodes.remove(0);
        expand(p.x, p.y);
    }
}

private void expand(int x, int y){
    int limXMin = x - 1, limXMax = x + 1, limYMin = y - 1, limYMax = y + 1;
    int value = map[x][y];

    // Check limits of screen
    if ( limXMin < 0 ) limXMin = 0;
    if ( limXMax > SCREEN_X_DIV - 1) limXMax = SCREEN_X_DIV - 1;

    if ( limYMin < 0 ) limYMin = 0;
    if ( limYMax > SCREEN_Y_DIV - 1) limYMax = SCREEN_Y_DIV - 1;

    for (int i = limXMin; i <= limXMax; i++){
        for (int j = limYMin; j <= limYMax; j++){
            if ( map[i][j] == 0 ) {
                if ( i != x || j != y ){
                    nodes.add(new Point(i, j));
                    map[i][j] = value + 1;
                }
            }
        }
    }
}

解释

我使用一个FIFO列表。我在其中添加节点,例如,流程如下:

(1) Add 0 position to expand node list.
(2) Expand 0 by setting 1 values arround it. Then add them to expand node list.
(2) Expand 1 by setting 2 values arround it. Then add them to expand node list.
(...)
(X) Expand 2 by setting 3 values arround it. Then add them to expand node list.
(Y) Expand 3 by setting 4 values arround it. Then add them to expand node list.
(...)
BKE

如前所述,您执行的操作称为广度优先搜索,这是Dijkstra算法的特例做得好,适合自己寻找!

问题在于,BFS的时间复杂度为O(V+E),其中V节点数,E边缘数。在您的情况下,将取决于地图的稀疏度(即,有多少X-es),取决于地图的大小。对于大小为1700x1440的地图,无论如何大约为数百万。

如果僵尸的数量不是太大,则使用启发式BFS的变体,为每个僵尸一一计算最短路径会更快得多(您仍然可以共享并重复使用僵尸之间的扩展节点)。例如,跳跃点搜索被均匀成本迷宫(跳跃点搜索是的一种特殊情况优化A星算法)。

此处的想法是采用起点(僵尸的位置)和终点(玩家的位置),并计算它们之间的最短路径,首先展开更靠近目的地的节点。这里更近意味着到端点的近似距离更短。到到达节点的距离是已知的,一颗星将选择一个节点,其中从起点到节点的距离之和加上从节点到终点的近似距离之和最小。由于您允许对角线移动,因此距离近似不能是曼哈顿距离,也不是Eucledian距离,因为近似值必须是实际距离的下限。你可以拿例如。max(│x-x'│,│y-y'│)。跳点搜索通过利用地图的迷宫结构进一步排除了其他节点,从而进一步改善了这一点。

该站点对几种此类算法进行了动画处理,因此您可以了解这些算法的工作原理。

这种方法的好处是,您不会搜索整个地图,而只搜索僵尸和玩家之间的一小部分。这可能已经比任何全尺寸BFS算法快了几个数量级。要显示加速效果有多大,请看以下图像。搜索仅探索标记的节点:

搜寻星星 跳点搜索

另一个优点是,您可以在运行时间和僵尸的“聪明”之间做出折衷。您所要做的就是始终不要一直运行这样的算法。您可以在预先定义的步骤数之后停止,并仅获得路径起点的近似值(通过查看起点和最有希望的节点之间的最短路径进行下一步扩展)。因此,根据您需要多少时间进行计算,您可能拥有最佳或较低的僵尸。

本文收集自互联网,转载请注明来源。

如有侵权,请联系[email protected] 删除。

编辑于
0

我来说两句

0条评论
登录后参与评论

相关文章