我有一张有向图 X-> Y Y-> Z
我想补充一下这个grpah传递闭包 X-> Z
我在算法中应该改变什么现在我在两个方向上创建x,y和z之间的所有可能组合。
我的代码如下。
def transitive_closure(G):
TC = nx.DiGraph()
TC.add_nodes_from(G.nodes())
TC.add_edges_from(G.edges())
for v in G:
TC.add_edges_from((v, u) for u in nx.dfs_preorder_nodes(G, source=v)
if v != u)
return TC
答案 0 :(得分:1)
您可以尝试迭代解决方案。首先,不要创建包含最后一个节点和边缘的新图形,而是复制它:
TC = G.copy()
然后迭代节点并将邻居的所有邻居添加为x
的邻居:
for x in G:
# Extract all neighbours of neighbours of x (from G)
all_nh = []
for y in G.neighbours(x):
all_nh += G.neighbours(y)
# Remove from the list of neighbors the current node and its immediate neighbors
all_nh = set(all_nh) - set([x]) - set(G.neighbours(x))
# Create new edges (x -> z)
edges = map(lambda z: (x, z), all_nh)
# Add them to the new graph
TC.add_edges_from(edges)
请注意,python中的set
是唯一值的容器,因此set(a) - set(b)
会从b
中删除a
的条目。
通过使用列表解析,可以减少提取邻居的所有邻居的for循环并且(可能加速)更多:
all_nh = [z for y in G.neighbors(x) for z in G.neighbors(y)]
产生这样的东西:
def transitive_closure(G):
TC = G.copy()
for x in G:
all_nh = [z for y in G.neighbors(x) for z in G.neighbors(y)]
all_nh = set(all_nh) - set([x]) - set(G.neighbors(x))
edges = map(lambda z: (x, z), all_nh)
TC.add_edges_from(edges)
return TC