最短路径问题

最短路径问题

一.迪克斯特朗算法

from IPython.display import Image
Image(filename="./data/9_01.png",width=800,height=960)

output_2_0.png

Image(filename="./data/9_02.png",width=800,height=960)

output_3_0.png

from collections import defaultdict
import sys

class Graph(object):
    def __init__(self):
        self.nodes=set()
        self.edges=defaultdict(list)
        self.distances={}
        
    def add_node(self,node):
        self.nodes.add(node)
        
    def add_edge(self,from_node,to_node,distance):
        self.edges[from_node].append(to_node)
        self.distances[(from_node,to_node)]=distance
class Node(object):
    def __init__(self,name):
        self.distance=sys.maxsize
        self.predecessor=None
        self.name=name
        
    def set_distance(self,dist):
        self.distance=dist
        
    def set_predecessor(self,pred):
        self.predecessor=pred
        
    def get_distance(self):
        return self.distance
    
    def get_predecessor(self):
        return self.predecessor
g=Graph()

g.add_node(Node("A"))
g.add_node(Node("B"))
g.add_node(Node("C"))
g.add_node(Node("D"))
g.add_node(Node("E"))
g.add_node(Node("F"))

g.add_edge("A","B",10)
g.add_edge("B","A",10)
g.add_edge("A","C",15)
g.add_edge("C","A",15)
g.add_edge("A","E",30)
g.add_edge("E","A",30)
g.add_edge("B","D",5)
g.add_edge("D","B",5)
g.add_edge("B","E",14)
g.add_edge("E","B",14)
g.add_edge("C","D",12)
g.add_edge("D","C",12)
g.add_edge("C","E",12)
g.add_edge("E","C",12)
g.add_edge("D","F",10)
g.add_edge("F","D",10)
g.add_edge("E","F",20)
g.add_edge("F","E",20)
permanent=set()
temporary=set()

temporary.add(initial)
---------------------------------------------------------------------------

NameError                                 Traceback (most recent call last)

<ipython-input-4-d4ac71f3607a> in <module>
      2 temporary=set()
      3 
----> 4 temporary.add(initial)


NameError: name 'initial' is not defined
while temporary:
    min_node=None
    
    for node in temporary:
        if min_node is None:
            min_node=node
        elif node.get_distance()<min_node.get_distance():
            min_node=node
            
    temporary.remove(min_node)
    
    permanent.add(min_node)
    current_distance=min_node.get_distance()
    
    for neighbour in graph.edges[min_node]:
        new_distance=current_distance+graph.distance[(min_node,neighbour)]
        
        if neighbour not in permanent and new_distance<neighbour.get_distance():
            neighbour.set_distance(new_distance)
            neighbour.set_predecessor(min_node)
            temporary.add(neighbour)
def printPath(self,end,predecessor):
    current=end
    path={end}
    
    while current.predecessor!=None:
        path.add(current.predecessor)
        current=current.predecessor
        
    path.reverse()
    print(path)

完整代码

from collections import defaultdict
import sys

class Graph(object):
    def __init__(self):
        self.nodes=set()
        self.edges=defaultdict(list)
        self.distances={}
        
    def add_node(self,node):
        self.nodes.add(node)
        
    def add_edge(self,from_node,to_node,distance):
        self.edges[from_node].append(to_node)
        self.distances[(from_node,to_node)]=distance
        
        
class Node(object):
    def __init__(self,name):
        self.distance=sys.maxsize
        self.predecessor=None
        self.name=name
        
    def set_distance(self,dist):
        self.distance=dist
        
    def set_predecessor(self,pred):
        self.predecessor=pred
        
    def get_distance(self):
        return self.distance
    
    def get_predecessor(self):
        return self.predecessor
    
    
def dijsktra(graph,initial,end):
    permanent={}
    temporary={}
    temporary.add(initial)
    initial.set_distance(0)
    
    while temporary:
        min_node=None
    
        for node in temporary:
            if min_node is None:
                min_node=node
            elif node.get_distance()<min_node.get_distance():
                min_node=node
            
        temporary.remove(min_node)
    
        permanent.add(min_node)
        current_distance=min_node.get_distance()
    
        for neighbour in graph.edges[min_node]:
            new_distance=current_distance+graph.distance[(min_node,neighbour)]
        
            if neighbour not in permanent and new_distance<neighbour.get_distance():
                neighbour.set_distance(new_distance)
                neighbour.set_predecessor(min_node)
                temporary.add(neighbour)

def printPath(self,end,predecessor):
    current=end
    path={end}
    
    while current.predecessor!=None:
        path.add(current.predecessor)
        current=current.predecessor
        
    path.reverse()
    print(path)

二.Floyd算法

Image(filename="./data/9_03.png",width=800,height=960)

output_13_0.png

Image(filename="./data/9_04.png",width=800,height=960)

output_14_0.png

import sys

class Floyd(object):
    def __init__(self):
        pass
    
    def solveFloyd(self,dist,start,end):
        n=len(dist)
        path=self.createPath(n)
        
        for k in range(n):
            for i in range(n):
                for j in range(n):
                    if dist[i][j]>dist[i][k]+dist[k][j]:
                        dist[i][j]=dist[i][k]+dist[k][j]
                        path[i][j]=path[i][k]
                        
                        
        self.printPath(start,path,end)
        
    def createPath(self,n):
        path=[]
        
        for i in range(n):
            row=[]
            
            for j in range(n):
                row.append(j)
            path.append(row)
            
        return path
    
    def printPath(self,current,path,end):
        solution=[]
        
        while current!=end:
            solution.append(current)
            current=path[current][end]
        solution.append(current)
        
        print(solution)
dist=[
    [0,10,15,sys.maxsize,30,sys.maxsize],
    [10,0,sys.maxsize,5,14,sys.maxsize],
    [15,sys.maxsize,0,12,12,sys.maxsize],
    [sys.maxsize,5,12,0,sys.maxsize,10],
    [30,14,12,sys.maxsize,0,20],
    [sys.maxsize,sys.maxsize,sys.maxsize,10,20,0]
]


Floyd().solveFloyd(dist,0,5)
[0, 1, 3, 5]

三.A*算法

Image(filename="./data/9_05.png",width=800,height=960)

output_18_0.png

原文地址:https://www.cnblogs.com/LQ6H/p/12940555.html