`A *`从边界移除一个节点

时间:2017-05-23 16:15:06

标签: python algorithm a-star

这是我编写的A*算法,在评估中我被告知“当后继者被添加到边界时,你的实现会执行目标测试,而不是当它被移除时:这会影响最优性”< / em>的。它是什么意思“不是什么时候被删除”?

这是我的代码:

def solve(problem, heuristic) :
    """ 
    A* search algorithm finding the shortest path.

    Returns:
        A list of actions.
    """
    s0 = problem.get_initial_state()
    queue = PriorityQueue()
    queue.push((0,s0,[]),0)  # second 0 is priority
    cost_so_far = dict()
    cost_so_far[s0] = 0

    while not queue.is_empty():
        current_cost, s, actions = queue.pop()
        for successor, action, cost in problem.get_successors(s):
            new_cost = current_cost + cost
            if problem.goal_test(successor):
                return actions + [action]
            else:
                h = heuristic(successor, problem)
                if successor not in cost_so_far or cost_so_far[successor] > new_cost + h:
                    cost_so_far[successor] = new_cost + h
                    queue.push((new_cost, successor, actions + [action]), new_cost + h)

修改后的版本(更新)

def solve(problem, heuristic) :
    """ 
    A* search algorithm finding the shortest path.

    Returns:
        A list of actions.
    """
    s0 = problem.get_initial_state()
    queue = PriorityQueue()
    queue.push((s0,[]),0)  # 0 is the priority
    cost_so_far = {s0:0}

    while not queue.is_empty():
        s, actions = queue.pop()

        if problem.goal_test(s):
                return actions

        for successor, action, cost in problem.get_successors(s):
            successor_cost = current_cost + cost
            new_cost = successor_cost + heuristic(successor, problem)

            if successor not in cost_so_far or cost_so_far[successor] > new_cost:
                    cost_so_far[successor] = new_cost
                    queue.push((successor, actions + [action]), new_cost)

2 个答案:

答案 0 :(得分:0)

在你引用之前的维基百科:&#34;上面的伪代码假设启发函数是单调的&#34;。

您的代码会在此图表和启发式上给出错误的答案(字母是节点,数字是成本):

urlpatterns = [
    url(r'^admin/', admin.site.urls),
    #leave it blank...
    url(r'^/', include('users.urls', namespace='users')),
    url(r'^home/', home, name='home'),
]

节点将按Get from X to Z: 1 2 X - Y - Z 1 \ W / 3 h(X) = 2, h(Y) = 2, h(W) = 1, h(Z) = 0 的顺序展开。但是,您的程序会在第一次找到X, W, Z, Y, Z后退出,并报告路径Z,其成本为4,这不是最佳的。

答案 1 :(得分:0)

说你的图表如下:

    9
S ----- G
 \     /
 1\   /1
   \ /
    W

您需要沿着最便宜的路径从起始节点S到达目标节点G。 S-G边缘的成本为9,而连接到航点W的边缘的成本为2。

您的算法会查看S的邻居,将节点添加到边界,找到G,然后立即返回昂贵的直接SG路径,而无需通过航点{{1 }}

相反,当您从优先级队列中W节点时,需要对节点执行目标测试。此时,您可以确保找到节点的最便宜路径,而不仅仅是节点的某些路径。