给定起点和终点,在图表中创建所有可能路径的列表

时间:2015-03-28 04:52:05

标签: python class graph path breadth-first-search

给定以下Graph类,它接受一个图形对象并输出它的邻接列表:

class Graph:
def __init__(self, graph_str):
    self.graph_str = []
    graph_str = graph_str.splitlines()
    for i in graph_str:
        i = (i.split())
        self.graph_str.append(i)
    directed_helper = self.graph_str[0]
    directed_score = directed_helper[0]
    weighted_helper = self.graph_str[0]
    weighted_score = weighted_helper[1]
    self.weighted = weighted_score
    self.directed = directed_score
    self.graph_str.pop(0)
    if self.directed == ("D"):
        self.directed = True
    elif self.directed == ("U"):
        self.directed = False
    if self.weighted == ("W"):
        self.weighted = True
    elif self.weighted != ("W"):
        self.weighted = False
    if self.weighted == False:
        self.edge_number = graph_str[0]
        self.edge_number = list(self.edge_number)
        self.edge_number = self.edge_number[2]
        self.edge_number = int(self.edge_number)
        self.adjacency_list = [[] for _ in range(self.edge_number)]  
    elif self.weighted == True:
        self.edge_number = graph_str[0]
        self.edge_number = list(self.edge_number)
        self.edge_number = self.edge_number[4]
        self.edge_number = int(self.edge_number)
        self.adjacency_list = [[] for _ in range(self.edge_number)]             
    if self.weighted == False:
        if self.directed == True:
            for s in self.graph_str:
                self.first_element = s[0]
                self.first_element = int(self.first_element)
                self.second_element = s[1]
                self.second_element = int(self.second_element)
                self.adjacency_list[self.first_element].append((self.second_element, None))
        elif self.directed == False:
            for t in self.graph_str:
                self.first_element = t[0]
                self.first_element = int(self.first_element)
                self.second_element = t[1]
                self.second_element = int(self.second_element)
                self.adjacency_list[self.first_element].append((self.second_element, None))
                self.adjacency_list[self.second_element].append((self.first_element, None))
    elif self.weighted == True:
        if self.directed == True:
            for t in self.graph_str:
                self.first_element = t[0]
                self.first_element = int(self.first_element)
                self.second_element = t[1]
                self.second_element = int(self.second_element)
                self.third_element = t[2]
                self.third_element = int(self.third_element)
                self.adjacency_list[self.first_element].append((self.second_element, self.third_element))
        if self.directed == False:
            for t in self.graph_str:
                self.first_element = t[0]
                self.first_element = int(self.first_element)
                self.second_element = t[1]
                self.second_element = int(self.second_element)
                self.third_element = t[2]
                self.third_element = int(self.third_element)
                self.adjacency_list[self.first_element].append((self.second_element, self.third_element))
                self.adjacency_list[self.second_element].append((self.first_element, self.third_element))
    (self.adjacency_list)

以下函数在同一个图形对象上执行广度优先搜索:

def bfs_tree(graph, start):
graph = Graph(graph_str)
parent_array = []
found_parent = []
empty_list = []
for _ in graph.adjacency_list:
    parent_array.append(None)
    found_parent.append(False)
empty_list. append(start)
found_parent[start] = True
while len(empty_list) != 0:
    element = empty_list.pop()
    for i in graph.adjacency_list[element]:
        if found_parent[i[0]] == False:
            found_parent[i[0]] = True
            parent_array[i[0]] = element
            empty_list.insert(0, i[0])
return parent_array

我希望使用回溯来编写一个函数allpaths(图形,源,目标),它接受一个图形对象,一个源顶点(整数)和一个目标顶点(整数),并返回所有可能路径的列表。源顶点到目标顶点不包含任何循环。路径是顶点列表,其中第一个元素是源顶点,最后一个元素是目标顶点,中间的元素(如果有)是沿路径的顶点。

例如:

# triangle graph
graph_str = """\
U 3
0 1
1 2
2 0
"""

print(sorted(allpaths(Graph(graph_str), 0, 2)))

应输出:

[[0, 1, 2], [0, 2]]

和此:

graph_str = """\
U 5
0 2
1 2
3 2
4 2
1 4
"""

print(sorted(allpaths(Graph(graph_str), 0, 1)))

应输出:

[[0, 2, 1], [0, 2, 4, 1]]

到目前为止,我有:

def allpaths (graph, source, destination):
    graph = Graph(graph_str)
    parents = bfs_tree(graph, 0)
    counter = 0
    array_a = []
    array_a_2 = []
    for i in parents:
        if len(parents) >= counter:
            if parents[counter] == source:
                if len(parents) > counter+1:
                    a = counter
                else:
                    a = (counter)
            else:
                counter+=1
    for a in parents[counter:]:
        array_a.append(a)
    for c in parents:
        if destination not in parents and parents[0] != None:
            if c not in array_a:
                array_a.append(c)
    array_a.append(destination)
    if None in array_a:
        array_a.remove(None)
    for b in array_a:
        if b not in array_a_2:
            array_a_2.append(b)
    return (array_a_2)

只输出一条路径,而不是全部路径,我不确定如何继续这样做。

非常感谢任何有关此问题的帮助:)

1 个答案:

答案 0 :(得分:-1)

您想自己编写此算法吗?我只是问,因为看起来你正在寻找的是精彩图库networkx中的all_simple_paths函数。