我正在使用networkx.all_simple_paths(G,source,dest)
找出两个节点之间的所有可能路径。我返回多个列表。
这是我的代码段:
for path in (nx.all_simple_paths(G,source=node1,target=node2):
print path
这为我提供了存储路径的多个列表。 我需要找出给定节点对之间是否只有一条路径。
我该怎么做?
感谢。
答案 0 :(得分:2)
不是绝对最干净的,但这是一个查看迭代器的函数。如果没有第一个元素,则返回False
。如果存在第一个元素(即,存在路径),但没有第二个元素,则返回True
。如果存在第二个(即,存在多个路径),则返回False
。它永远不会检查是否还有。
def simple_path(G,source,target):
iterator = nx.all_simple_paths(G,source=source,target=target)
try:
first_path = next(iterator)
except StopIteration:
return False
try:
second_path = next(iterator)
except StopIteration:
return True
return False
样品运行:
In [3]: G= nx.Graph()
In [4]: G.add_edges_from([(1,2),(1,3),(2,3),(3,4)])
In [5]: simple_path(G,1,2)
Out[5]: False
In [6]: simple_path(G,1,3)
Out[6]: False
In [7]: simple_path(G,3,4)
Out[7]: True
In [8]: simple_path(G,1,4)
Out[8]: False
答案 1 :(得分:1)
您可以使用zip
将前两个潜在路径匹配在一起(列表内容不重要,这就是我放_
的原因)。结果对象的长度是找到的路径数:
paths = nx.all_simple_paths(G,source=node1,target=node2))
# True, if there was exactly one path, calculates at most 2 paths
is_unique_path = len(zip([_, _], paths)) == 1
答案 2 :(得分:1)
如果您想知道此图g1
的节点0和1之间是否存在单个路径,例如:
len([path for path in nx.all_simple_paths(g1, source=0, target=1)]) == 1 # True
如果存在特定数量的路径,您可以对此进行扩展以检查所有节点,并为该特定节点对返回True / False列表。
import itertools
def number_paths(graph, number):
# list of all possible pairs. NOTE: there may not be an edge between some pairs
node_pairs = list(itertools.combinations(graph.nodes(), 2))
num_path = []
for pair in node_pairs:
num_path.append(
len([path for path in nx.all_simple_paths(graph, source=pair[0], target=pair[1])]) == number )
return num_path, node_pairs
因此,对于上图,您可以这样做:
print number_paths(g1, 1) # prints: ([True], [(0, 1)])
更好的示例是此图g2
:
节点对之间是否只存在一条路径?
check, nodes = number_paths(g2, 1)
print 'check:', check # check: [True, False, False, False, False, False]
print 'nodes:', nodes # nodes: [(0, 1), (0, 2), (0, 3), (1, 2), (1, 3), (2, 3)]
节点对之间是否只存在2条路径?
check, nodes = number_paths(g2, 2)
print 'check:', check # check: [False, True, True, True, True, True]
print 'nodes:', nodes # nodes: [(0, 1), (0, 2), (0, 3), (1, 2), (1, 3), (2, 3)]
答案 3 :(得分:1)
受Joel的回答启发,避免生成两个以上的路径并通过异常捕获进行分支:
import itertools
def simple_path(G,source,target):
iterator = nx.all_simple_paths(G,source=source,target=target)
return sum(1 for _ in itertools.islice(iterator, 2)) == 1
它尝试从发生器计算最多2个元素。
它应返回False
是否有零或两个元素,如果只有一个元素,则返回True
。
答案 4 :(得分:0)
您可以将next
与default
参数一起使用:
def has_one_path(G, source, target):
paths = nx.all_simple_paths(G, source, target)
return next(paths, None) is not None and next(paths, None) is None
我认为它非常具有可读性和效率:如果有下一个路径,图表有一条从源到目标的路径,之后没有下一条路径。