dfs来实现一个图形,python

dfs来实现一个图形,python,python,graph,depth-first-search,Python,Graph,Depth First Search,我试图在python中使用dfs实现一个图,以找到从“a”到“F”的所有可能路径。 图表为: graph = {'A': ['B', 'C'], 'B': ['A', 'D', 'E'], 'C': ['A', 'F'], 'D': ['B'], 'E': ['B', 'F'], 'F': ['C', 'E']} 下面是我的代码: def dfs_path(graph,start,end): re

我试图在python中使用dfs实现一个图,以找到从“a”到“F”的所有可能路径。 图表为:

graph = {'A': ['B', 'C'],
         'B': ['A', 'D', 'E'],
         'C': ['A', 'F'],
         'D': ['B'],
         'E': ['B', 'F'],
         'F': ['C', 'E']}
下面是我的代码:

def dfs_path(graph,start,end):
    res = []
    dfs(graph,start,end,[],res)
    return res
def dfs(graph,start,end,path,res):
    path+=[start]
    if start == end:
        res+=[path]
    elif not graph.has_key(start):
        return
    else:
        for node in graph[start]:
            if node not in path:
                dfs(graph,node,end,path,res)
print dfs_path(graph,'A','F')
通过打印的过程,我没有得到我想要的,而是得到了[['A','B','D','E','F','C']]

有人能告诉我我的代码有什么问题吗?如果可能的话,我想知道用同样的格式编写代码的正确方法。
谢谢

问题在于您的回溯。搜索从A->B->D开始,在D处到达死胡同,因为唯一的后继者是已经访问过的B。所以它会备份,但您没有从res中删除D。它只是停留在那里,所以当它继续使用E->F时,您的结果中仍然有D。

基本问题是只有一条路径。对dfs进行递归调用时,它会修改路径。当调用返回时,它不会恢复path的旧值。解决方法是将path的副本传递给dfs。注意递归调用中的路径[:]

第二个问题是,当您找到一条路径时,您将它与res连接起来,而实际上您希望将它附加到res

在下面的代码中,我取消了对start是否是图形中的键的检查。如果它不是图中的键,就不可能传递给函数

这张照片

[['A', 'B', 'E', 'F'], ['A', 'C', 'F']]  
在我看来这是正确的


我想说的是,您的函数基本上是正确的,但是您需要检查python列表的技术细节,以及通常可能的可变数据结构

这是一个带有迭代的DFS算法

def dfs(graph, start):

    vertex=start

    visited, stack = [vertex], [vertex]  #add start index to both visited and stack   

    while stack:    #while stack is not empty
        #for each of the children of current vertex we find the first non visited child and add it to visited as well as stack

        for i,each in enumerate(graph[vertex]):  
            if each not in visited:
                visited.append(each)
                stack+=[each]    #push the element to stack if it is visited
                vertex=each      #change current vertex to last visited vertex
                break            #since the stack keeps track of the order of elements we can jump to children of current vertex.
            else:
                #if the length of children of a vertex is reached and all children are visited then pop the last element from stack
                if i==len(graph[vertex])-1:   
                    vertex=stack.pop() 
                    break
                else:
                    continue    #continue till the end to check if all the children of current vertex are visited
    return visited
graph = {'A': ['B', 'C'],
     'B': ['A', 'D', 'E'],
     'C': ['A', 'F'],
     'D': ['B'],
     'E': ['B', 'F'],
     'F': ['C', 'E']}
dfs(graph,'A')
我的建议是使用一个集合来跟踪您访问过的节点。将开始添加到dfs开头的集合中。迭代start的后续项时,跳过作为集合成员的后续项。否则将递归,如果找到解决方案,则返回[start]+解决方案。如果退出循环而不返回,则返回None
def dfs(graph, start):

    vertex=start

    visited, stack = [vertex], [vertex]  #add start index to both visited and stack   

    while stack:    #while stack is not empty
        #for each of the children of current vertex we find the first non visited child and add it to visited as well as stack

        for i,each in enumerate(graph[vertex]):  
            if each not in visited:
                visited.append(each)
                stack+=[each]    #push the element to stack if it is visited
                vertex=each      #change current vertex to last visited vertex
                break            #since the stack keeps track of the order of elements we can jump to children of current vertex.
            else:
                #if the length of children of a vertex is reached and all children are visited then pop the last element from stack
                if i==len(graph[vertex])-1:   
                    vertex=stack.pop() 
                    break
                else:
                    continue    #continue till the end to check if all the children of current vertex are visited
    return visited
graph = {'A': ['B', 'C'],
     'B': ['A', 'D', 'E'],
     'C': ['A', 'F'],
     'D': ['B'],
     'E': ['B', 'F'],
     'F': ['C', 'E']}
dfs(graph,'A')
#Last In First Out
def dfs(G,Source,Goal):
    stack=[]
    stack_visited_result=[]
    stack.append(Source)
    stack_visited_result.append(Source)
    while len(stack)>0:
        print("**********STEP-",len(stack),"**********")
        r=0
        v=stack[-1]
        print("The current stack is ",stack);
        if(len(G.get(v))<=0):
            print("No key value for the top of the stack",x)
            stack.pop()
            v=stack[-1]
            print("After popping stack",stack)
        print ("top of the stack = " , v)
        for x in G[v]:
            if x not in stack_visited_result:
                r=1
                print ("value of x(ADJACENT VERTICES) " , x)
                stack.append(x)
                print("stack ",stack)
                if(stack[-1]==Goal):
                    print("--DESTINATION REACHED----")
                    print("RESULT FOR DFS ",stack_visited_result)   
                    quit()
                stack_visited_result.append(x)
                print("stack-visited ",stack_visited_result)
                break
        if(r is not 1):
                print("already visited so,pop the element")
                stack.pop()             
G={1:[2,3],2:[4,5,6],3:[],4:[],5:[7],6:[],7:[8],8:[]}
dfs(G,1,3)




This code will be used in case of directed graph