【问题标题】:Improving BFS performance with some kind of memoization通过某种记忆来提高 BFS 性能
【发布时间】:2019-06-05 18:14:24
【问题描述】:

我有这个问题,我正在尝试构建一种算法,该算法将在图中找到从一个顶点到其他顶点的距离。

假设我的网络看起来像这样一个非常简单的例子:

network = [[0,1,2],[2,3,4],[4,5,6],[6,7]]

我创建了一个 BFS 代码,它应该找到从指定源到其他图形顶点的路径长度

from itertools import chain
import numpy as np

n = 8
graph = {}

for i in range(0, n):
    graph[i] = []

for communes in communities2:
    for vertice in communes:
        work = communes.copy()
        work.remove(vertice)
        graph[vertice].append(work)

for k, v in graph.items():

    graph[k] = list(chain(*v))

def bsf3(graph, s):
    matrix = np.zeros([n,n])
    dist = {}
    visited = []
    queue = [s]
    dist[s] = 0
    visited.append(s)
    matrix[s][s] = 0

    while queue:

        v = queue.pop(0)
        for neighbour in graph[v]:

            if neighbour in visited:
                pass
            else:

                matrix[s][neighbour] = matrix[s][v] + 1


                queue.append(neighbour)
                visited.append(neighbour)



    return matrix

bsf3(graph,2)

首先我正在创建图形(字典),然后使用该函数来查找距离。

我担心的是这种方法不适用于更大的网络(假设其中有 1000 人)。我正在考虑的是使用某种记忆(实际上这就是我制作矩阵而不是列表的原因)。这个想法是,当算法计算从 0 到 3 的路径(它已经做了什么)时,它应该以 matrix[1][3] = 1 等方式跟踪其他路线。

所以我会使用像 bsf3(graph, 1) 这样的函数,它不会从头开始计算所有内容,但能够访问矩阵中的一些值。

提前致谢!

【问题讨论】:

  • 我不明白这个问题 - BFS 已经将与先前节点的距离用于后续节点。我在您的代码中看到的唯一问题是 visited 应该是一个集合,而不是一个列表。
  • 但是有没有办法让它更快?我已将访问更改为设置,但是当我在拥有 5000 个成员的网络上运行此代码时,代码运行速度非常慢。太慢了,我不确定它是否会产生任何结果或者它只是被打破了。

标签: python algorithm graph shortest-path


【解决方案1】:

知道这一点并不能完全回答您的问题,但这是您可以尝试的另一种方法。

在网络中,您将为网络中的每个节点提供一个路由表。您只需保存网络内所有节点的列表以及您必须去的节点。节点D的路由表示例

A -> B
B -> B
C -> E
D -> D
E -> E

您需要在每个节点上运行 BFS 来构建所有路由表,它将占用 O(|V|*(|V|+|E|)。空间复杂度是二次的,但您必须检查所有可能的路径。

当您创建所有这些信息时,您可以简单地从一个节点开始,在表中搜索您的目标节点并找到下一个要去的节点。这将提供更好的时间复杂度(如果您为表使用正确的数据结构)。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-08-19
    • 1970-01-01
    • 2018-01-20
    • 2014-11-25
    • 2018-07-26
    相关资源
    最近更新 更多