[英]Find all possible paths in a python graph data structure without using recursive function
在我的 csv 文件中查找所有可能的路徑時遇到一個嚴重的問題,如下所示:
資源 | 目標 | 源代碼庫 | 目標倉庫 |
---|---|---|---|
來源1 | 目標2 | 回購-1 | 回購-2 |
來源5 | 目標3 | 回購5 | 回購3 |
來源8 | 目標5 | 回購8 | 回購5 |
數據集中有大量的行,超過 5000 行。 我想像這樣生成所有可能的路徑並返回一個列表(Target5 等於 SOURCE5):
我想在不使用遞歸函數的情況下實現此解決方案,因為會導致問題(超出最大遞歸深度)。
這是當前的代碼示例:
def attach_co_changing_components(base_component):
co_changes = df_depends_on.loc[df_depends_on["Source_repo"] ==
base_component, "Target_repo"].values
result = {base_component: list(co_changes)}
return result
def dfs(data, path, paths):
datum = path[-1]
if datum in data:
for val in data[datum]:
new_path = path + [val]
paths = dfs(data, new_path, paths)
else:
paths += [path]
return paths
def enumerate_paths(graph, nodes=[]):
nodes = graph.keys()
all_paths = []
for node in nodes:
node_paths = dfs(graph, [node], [])
all_paths += node_paths
return all_paths
if __name__ == "__main__":
df = pd.read_csv("clean_openstack_evolution.csv")
co_changing_components = df[["Source"]].copy()
co_changing_components = co_changing_components.drop_duplicates(
).reset_index(drop=True)
co_changing_components = co_changing_components["Source"].map(
attach_co_changing_components)
co_changing_components = co_changing_components.rename("Path")
co_changing_components = co_changing_components.reset_index(drop=True)
newdict = {}
for k, v in [(key, d[key]) for d in co_changing_components for key in d]:
if k not in newdict: newdict[k] = v
else: newdict[k].append(v)
graph_keys = df_depends_on["Source_repo"].drop_duplicates().to_dict(
).values()
graph_keys = {*graph_keys}
graph_keys = set([
k for k in graph_keys
if len(df_depends_on[df_depends_on["Target"] == k]) > 0
])
result = enumerate_paths(new_dict)
執行上述代碼后的 output 如下:
這是谷歌驅動器的數據鏈接
我嘗試使用遞歸function來解決問題,但是代碼失敗,出現了超出深度的問題。 我的目標是在沒有遞歸函數的情況下解決它。
我不確定您是否想要所有路徑或專門從節點到另一個節點的路徑。 無論哪種方式,這看起來都像是networkx
的工作。
nx.from_pandas_edgelist
)import networkx as nx
import pandas as pd
df = pd.read_csv("...")
graph = nx.from_pandas_edgelist(df, create_using=nx.DiGraph)
nx.all_simple_paths
)from itertools import chain, product, starmap
from functools import partial
roots = (node for node, d in graph.in_degree if d == 0)
leaves = (node for node, d in graph.out_degree if d == 0)
all_paths = partial(nx.all_simple_paths, graph)
paths = list(chain.from_iterable(starmap(all_paths, product(roots, leaves))))
source_node = "some_node_in_graph"
target_node = "some_other_node_in_graph"
list(nx.all_simple_paths(graph, source=source_node, target=target_node))
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.