forked from adinloh/Algorithms-design-and-analysis
-
Notifications
You must be signed in to change notification settings - Fork 0
/
10) All Pairs Shortest Paths - Floyd-Warshall.py
59 lines (46 loc) · 1.66 KB
/
10) All Pairs Shortest Paths - Floyd-Warshall.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
import sys
infinity = sys.maxint
def floyd_warshall(n, edges):
# Do not use NxNxN arrays!
# All we need at each step is the result
# of the previous turn, so NxNx2 is sufficient.
A = [[[infinity for _ in xrange(n)] for _ in xrange(n)] for _ in xrange(2)]
# Base cases
for i in xrange(n):
for j in xrange(n):
if i == j:
A[0][i][j] = 0
else:
if ('%i,%i' % (i, j)) in edges:
A[0][i][j] = edges['%i,%i' % (i, j)]
else:
A[0][i][j] = infinity
# Dynamic programming algorithm
for k in xrange(1, n+1):
for i in xrange(n):
for j in xrange(n):
A[k % 2][i][j] = min(A[(k-1) % 2][i][j], A[(k-1) % 2][i][k-1] + A[(k-1) % 2][k-1][j]) # a bit modified because of 0-based arrays
# Check for negative cycles
for i in xrange(n):
if A[n % 2][i][i] < 0: return None
return A[n % 2]
def main():
for i in [1,2,3]:
print 'Graph %i:' % i
f = open('graph%i.txt' % i)
n, m = [int(x) for x in f.readline().split()]
edges = {}
for line in f:
u, v, w = [int(x) for x in line.split()]
edges['%i,%i' % (u, v)] = w
APSP = floyd_warshall(n, edges)
if APSP is None:
print ' There is a negative-cost cycle'
else:
shortest = infinity
for u in xrange(n):
for v in xrange(n):
if APSP[u][v] < shortest:
shortest = APSP[u][v]
print ' Shortest shortest path: %i' % shortest
main()