A星算法,更新节点的G成本

我这里有一个基本可用的A星算法。它能够找到通往目的地的路径,但是如果有更好的路径可用时,它无法更新路径。

例如:

s = 起点e = 终点x = 墙. = 路径

它现在是这样做的:

       xs......x   e      .x  .      .x .      .x.       .

而我希望它这样做:

       xs .    x   e   .   x  .    .  x .     . x.       .

我需要的是当有更低的G成本的节点可用时,瓦片(节点)能够更改它们的父节点。实现这一点确实是个挑战。

任何帮助都将不胜感激,

谢谢

    map = [['w','w','w','w','w'],['w','w','x','w','w'],['w','w','x','w','w'],['w','w','x','w','w'],['w','w','w','w','w'],]""" make copy of dict in the function! """tile_data = {}class Tile:    def __init__(self, pos, char):        self.pos = pos        self.char = char        self.parent = None        self.H = 0        self.G = float('inf')        self.F = 0#Gen Tilesfor y in range(len(map)):    for x in range(len(map[0])):        char = map[y][x]        tile = Tile((x,y), char)        tile_data[(x,y)] = tiledef a_star(start, end, map):    unchecked_tiles = []    checked_tiles = []    # set start position    tile_data[start].parent = None    tile_data[start].pos = start    tile_data[start].G = 0    unchecked_tiles.append(tile_data[start])    while unchecked_tiles:        #Get the tile with lowest F score        current_tile = min(unchecked_tiles, key=lambda tile: tile.F)        #move tile to checked list        checked_tiles.append(current_tile)        unchecked_tiles.remove(current_tile)        # If the End is found return the path of parent tiles        if current_tile.pos == end:            path = []            while current_tile.parent is not None:                path.append(current_tile.pos)                # Sets current tile to parent tile                current_tile = current_tile.parent            for tile in path:                print(tile, ": F = ", tile_data[tile].F, ": G = ", tile_data[tile].G, ": H = ", tile_data[tile].H)            return path[::-1] # Return reversed path        # Gets valid neighbors for current tile        neighbors = []        for dir in [(0, -1), (0, 1), (-1, 0), (1, 0), (-1, -1), (-1, 1), (1, -1), (1, 1)]:            #get tile pos            neighbor = (current_tile.pos[0] + dir[0], current_tile.pos[1] + dir[1])            #check if tile on map and is valid            if 0 <= neighbor[0] < len(map[0]) and 0 <= neighbor[1] < len(map) and tile_data[neighbor].char == 'w' and tile_data[neighbor] not in checked_tiles:                # Set parent for neighbors                tile_data[neighbor].parent = current_tile                # Add neighbor to lists                unchecked_tiles.append(tile_data[neighbor])                neighbors.append(neighbor)        for neighbor in neighbors:            # Set G cost (14 for diagonal, 10 for othogonal move + parent.G cost)            if tile_data[neighbor].pos[0] == current_tile.pos[0] or tile_data[neighbor].pos[1] == current_tile.pos[1]:                tile_data[neighbor].G = 10 + current_tile.G            else:                                           tile_data[neighbor].G = 14 + current_tile.G                        if tile_data[neighbor].G < current_tile.G:                current_tile.parent = tile_data[neighbor].parent            # Set H cost (a**2 + b**2 = c**2)            tile_data[neighbor].H = ((neighbor[0] - end[0]) ** 2) + ((neighbor[1] - end[1]) ** 2)            # Set F cost (G + H)            tile_data[neighbor].F = tile_data[neighbor].H + tile_data[neighbor].G    print('finished')a_star((0,2),(4,2),map)

回答:

问题是我之前将重复的邻居节点移动到“未检查”列表中时,G成本是错误的。无论如何,这里有一个可用的A星算法 🙂

”’

map = [['w','w','w','w','w'],['w','w','x','w','w'],['w','w','x','w','w'],['w','w','x','w','w'],['w','w','w','w','w'],]""" make copy of dict in the function! """tile_data = {}class Tile:    def __init__(self, pos, char):        self.pos = pos        self.char = char        self.parent = None        self.H = 0        self.G = 0        self.F = 0#Gen Tilesfor y in range(len(map)):    for x in range(len(map[0])):        char = map[y][x]        tile = Tile((x,y), char)        tile_data[(x,y)] = tiledef a_star(start, end, map):    unchecked_tiles = []    checked_tiles = []    # set start position    tile_data[start].parent = None    tile_data[start].pos = start    tile_data[start].G = 0    unchecked_tiles.append(tile_data[start])    while unchecked_tiles:        #Get the tile with lowest F score        current_tile = min(unchecked_tiles, key=lambda tile: tile.F)        #move tile to checked list        checked_tiles.append(current_tile)        unchecked_tiles.remove(current_tile)        # If the End is found return the path of parent tiles        if current_tile.pos == end:            path = []            while current_tile.parent is not None:                path.append(current_tile.pos)                # Sets current tile to parent tile                current_tile = current_tile.parent            for tile in path:                print(tile, ": F = ", tile_data[tile].F, ": G = ", tile_data[tile].G, ": H = ", tile_data[tile].H)            return path[::-1] # Return reversed path        # Gets valid neighbors for current tile        neighbors = []        for dir in [(0, -1), (0, 1), (-1, 0), (1, 0), (-1, -1), (-1, 1), (1, -1), (1, 1)]:            #get tile pos            neighbor = (current_tile.pos[0] + dir[0], current_tile.pos[1] + dir[1])            #check if tile on map and is valid            if 0 <= neighbor[0] < len(map[0]) and 0 <= neighbor[1] < len(map) and tile_data[neighbor].char == 'w' and tile_data[neighbor] not in checked_tiles:                if tile_data[neighbor] not in unchecked_tiles:                    # Add neighbor to lists                    unchecked_tiles.append(tile_data[neighbor])                    neighbors.append(neighbor)                    # Set parent for neighbors                    tile_data[neighbor].parent = current_tile        for neighbor in neighbors:            # Set G cost (14 for diagonal, 10 for othogonal move + parent.G cost)            if tile_data[neighbor].pos[0] == current_tile.pos[0] or tile_data[neighbor].pos[1] == current_tile.pos[1]:                tile_data[neighbor].G = 10 + current_tile.G            else:                                           tile_data[neighbor].G = 14 + current_tile.G                        if tile_data[neighbor].G < current_tile.G:                current_tile.parent = tile_data[neighbor].parent                if tile_data[neighbor].pos[0] == current_tile.pos[0] or tile_data[neighbor].pos[1] == current_tile.pos[1]:                    current_tile.G = tile_data[neighbor].G + 10                else:                    current_tile.G = tile_data[neighbor].G + 14            # Set H cost (a**2 + b**2 = c**2)            tile_data[neighbor].H = ((neighbor[0] - end[0]) ** 2) + ((neighbor[1] - end[1]) ** 2)            # Set F cost (G + H)            tile_data[neighbor].F = tile_data[neighbor].H + tile_data[neighbor].G    print('finished')a_star((0,2),(4,2),map)

”’

Related Posts

使用LSTM在Python中预测未来值

这段代码可以预测指定股票的当前日期之前的值,但不能预测…

如何在gensim的word2vec模型中查找双词组的相似性

我有一个word2vec模型,假设我使用的是googl…

dask_xgboost.predict 可以工作但无法显示 – 数据必须是一维的

我试图使用 XGBoost 创建模型。 看起来我成功地…

ML Tuning – Cross Validation in Spark

我在https://spark.apache.org/…

如何在React JS中使用fetch从REST API获取预测

我正在开发一个应用程序,其中Flask REST AP…

如何分析ML.NET中多类分类预测得分数组?

我在ML.NET中创建了一个多类分类项目。该项目可以对…

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注