Floyd-Warshall algorithm: Difference between revisions

Content added Content deleted
(Added 11l)
(Rename Perl 6 -> Raku, alphabetize, minor clean-up)
Line 27: Line 27:
* [https://www.youtube.com/watch?v=8WSZQwNtXPU Floyd-Warshall Algorithm - step by step guide (youtube)]
* [https://www.youtube.com/watch?v=8WSZQwNtXPU Floyd-Warshall Algorithm - step by step guide (youtube)]
<br><br>
<br><br>

=={{header|11l}}==
=={{header|11l}}==
{{trans|Python}}
{{trans|Python}}
Line 270: Line 271:
4 -> 3 1 4->2->1->3
4 -> 3 1 4->2->1->3
</pre>
</pre>

=={{header|C sharp|C#}}==
{{trans|Java}}
<lang csharp>using System;

namespace FloydWarshallAlgorithm {
class Program {
static void FloydWarshall(int[,] weights, int numVerticies) {
double[,] dist = new double[numVerticies, numVerticies];
for (int i = 0; i < numVerticies; i++) {
for (int j = 0; j < numVerticies; j++) {
dist[i, j] = double.PositiveInfinity;
}
}

for (int i = 0; i < weights.GetLength(0); i++) {
dist[weights[i, 0] - 1, weights[i, 1] - 1] = weights[i, 2];
}

int[,] next = new int[numVerticies, numVerticies];
for (int i = 0; i < numVerticies; i++) {
for (int j = 0; j < numVerticies; j++) {
if (i != j) {
next[i, j] = j + 1;
}
}
}

for (int k = 0; k < numVerticies; k++) {
for (int i = 0; i < numVerticies; i++) {
for (int j = 0; j < numVerticies; j++) {
if (dist[i, k] + dist[k, j] < dist[i, j]) {
dist[i, j] = dist[i, k] + dist[k, j];
next[i, j] = next[i, k];
}
}
}
}

PrintResult(dist, next);
}

static void PrintResult(double[,] dist, int[,] next) {
Console.WriteLine("pair dist path");
for (int i = 0; i < next.GetLength(0); i++) {
for (int j = 0; j < next.GetLength(1); j++) {
if (i != j) {
int u = i + 1;
int v = j + 1;
string path = string.Format("{0} -> {1} {2,2:G} {3}", u, v, dist[i, j], u);
do {
u = next[u - 1, v - 1];
path += " -> " + u;
} while (u != v);
Console.WriteLine(path);
}
}
}
}

static void Main(string[] args) {
int[,] weights = { { 1, 3, -2 }, { 2, 1, 4 }, { 2, 3, 3 }, { 3, 4, 2 }, { 4, 2, -1 } };
int numVerticies = 4;

FloydWarshall(weights, numVerticies);
}
}
}</lang>


=={{header|C++}}==
=={{header|C++}}==
Line 361: Line 430:
(4 -> 2, -1, 4 -> 2)
(4 -> 2, -1, 4 -> 2)
(4 -> 3, 1, 4 -> 2 -> 1 -> 3)</pre>
(4 -> 3, 1, 4 -> 2 -> 1 -> 3)</pre>

=={{header|C#|C sharp}}==
{{trans|Java}}
<lang csharp>using System;

namespace FloydWarshallAlgorithm {
class Program {
static void FloydWarshall(int[,] weights, int numVerticies) {
double[,] dist = new double[numVerticies, numVerticies];
for (int i = 0; i < numVerticies; i++) {
for (int j = 0; j < numVerticies; j++) {
dist[i, j] = double.PositiveInfinity;
}
}

for (int i = 0; i < weights.GetLength(0); i++) {
dist[weights[i, 0] - 1, weights[i, 1] - 1] = weights[i, 2];
}

int[,] next = new int[numVerticies, numVerticies];
for (int i = 0; i < numVerticies; i++) {
for (int j = 0; j < numVerticies; j++) {
if (i != j) {
next[i, j] = j + 1;
}
}
}

for (int k = 0; k < numVerticies; k++) {
for (int i = 0; i < numVerticies; i++) {
for (int j = 0; j < numVerticies; j++) {
if (dist[i, k] + dist[k, j] < dist[i, j]) {
dist[i, j] = dist[i, k] + dist[k, j];
next[i, j] = next[i, k];
}
}
}
}

PrintResult(dist, next);
}

static void PrintResult(double[,] dist, int[,] next) {
Console.WriteLine("pair dist path");
for (int i = 0; i < next.GetLength(0); i++) {
for (int j = 0; j < next.GetLength(1); j++) {
if (i != j) {
int u = i + 1;
int v = j + 1;
string path = string.Format("{0} -> {1} {2,2:G} {3}", u, v, dist[i, j], u);
do {
u = next[u - 1, v - 1];
path += " -> " + u;
} while (u != v);
Console.WriteLine(path);
}
}
}
}

static void Main(string[] args) {
int[,] weights = { { 1, 3, -2 }, { 2, 1, 4 }, { 2, 3, 3 }, { 3, 4, 2 }, { 4, 2, -1 } };
int numVerticies = 4;

FloydWarshall(weights, numVerticies);
}
}
}</lang>


=={{header|D}}==
=={{header|D}}==
Line 661: Line 662:
4 -> 2 -1 4 -> 2
4 -> 2 -1 4 -> 2
4 -> 3 1 4 -> 2 -> 1 -> 3
4 -> 3 1 4 -> 2 -> 1 -> 3
</pre>

=={{header|F_Sharp|F#}}==
===Floyd's algorithm===
<lang fsharp>
//Floyd's algorithm: Nigel Galloway August 5th 2018
let Floyd (n:'a[]) (g:Map<('a*'a),int>)= //nodes graph(Map of adjacency list)
let ix n g=Seq.init (pown g n) (fun x->List.unfold(fun (a,b)->if a=0 then None else Some(b%g,(a-1,b/g)))(n,x))
let fN w (i,j,k)=match Map.tryFind(i,j) w,Map.tryFind(i,k) w,Map.tryFind(k,j) w with
|(None ,Some j,Some k)->Some(j+k)
|(Some i,Some j,Some k)->if (j+k) < i then Some(j+k) else None
|_ ->None
let n,z=ix 3 (Array.length n)|>Seq.choose(fun (i::j::k::_)->if i<>j&&i<>k&&j<>k then Some(n.[i],n.[j],n.[k]) else None)
|>Seq.fold(fun (n,n') ((i,j,k) as g)->match fN n g with |Some g->(Map.add (i,j) g n,Map.add (i,j) k n')|_->(n,n')) (g,Map.empty)
(n,(fun x y->seq{
let rec fN n g=seq{
match Map.tryFind (n,g) z with
|Some r->yield! fN n r; yield Some r;yield! fN r g
|_->yield None}
yield! fN x y |> Seq.choose id; yield y}))
</lang>

===The Task===
<lang fsharp>
let fW=Map[((1,3),-2);((3,4),2);((4,2),-1);((2,1),4);((2,3),3)]
let N,G=Floyd [|1..4|] fW
List.allPairs [1..4] [1..4]|>List.filter(fun (n,g)->n<>g)|>List.iter(fun (n,g)->printfn "%d->%d %d %A" n g N.[(n,g)] (n::(List.ofSeq (G n g))))
</lang>
{{out}}
<pre>
1->2 -1 [1; 3; 4; 2]
1->3 -2 [1; 3]
1->4 0 [1; 3; 4]
2->1 4 [2; 1]
2->3 2 [2; 1; 3]
2->4 4 [2; 1; 3; 4]
3->1 5 [3; 4; 2; 1]
3->2 1 [3; 4; 2]
3->4 2 [3; 4]
4->1 3 [4; 2; 1]
4->2 -1 [4; 2]
4->3 1 [4; 2; 1; 3]
</pre>
</pre>


Line 743: Line 786:
4 -> 2 -1 4 -> 2
4 -> 2 -1 4 -> 2
4 -> 3 1 4 -> 2 -> 1 -> 3
4 -> 3 1 4 -> 2 -> 1 -> 3
</pre>

=={{header|F_Sharp|F#}}==
===Floyd's algorithm===
<lang fsharp>
//Floyd's algorithm: Nigel Galloway August 5th 2018
let Floyd (n:'a[]) (g:Map<('a*'a),int>)= //nodes graph(Map of adjacency list)
let ix n g=Seq.init (pown g n) (fun x->List.unfold(fun (a,b)->if a=0 then None else Some(b%g,(a-1,b/g)))(n,x))
let fN w (i,j,k)=match Map.tryFind(i,j) w,Map.tryFind(i,k) w,Map.tryFind(k,j) w with
|(None ,Some j,Some k)->Some(j+k)
|(Some i,Some j,Some k)->if (j+k) < i then Some(j+k) else None
|_ ->None
let n,z=ix 3 (Array.length n)|>Seq.choose(fun (i::j::k::_)->if i<>j&&i<>k&&j<>k then Some(n.[i],n.[j],n.[k]) else None)
|>Seq.fold(fun (n,n') ((i,j,k) as g)->match fN n g with |Some g->(Map.add (i,j) g n,Map.add (i,j) k n')|_->(n,n')) (g,Map.empty)
(n,(fun x y->seq{
let rec fN n g=seq{
match Map.tryFind (n,g) z with
|Some r->yield! fN n r; yield Some r;yield! fN r g
|_->yield None}
yield! fN x y |> Seq.choose id; yield y}))
</lang>

===The Task===
<lang fsharp>
let fW=Map[((1,3),-2);((3,4),2);((4,2),-1);((2,1),4);((2,3),3)]
let N,G=Floyd [|1..4|] fW
List.allPairs [1..4] [1..4]|>List.filter(fun (n,g)->n<>g)|>List.iter(fun (n,g)->printfn "%d->%d %d %A" n g N.[(n,g)] (n::(List.ofSeq (G n g))))
</lang>
{{out}}
<pre>
1->2 -1 [1; 3; 4; 2]
1->3 -2 [1; 3]
1->4 0 [1; 3; 4]
2->1 4 [2; 1]
2->3 2 [2; 1; 3]
2->4 4 [2; 1; 3; 4]
3->1 5 [3; 4; 2; 1]
3->2 1 [3; 4; 2]
3->4 2 [3; 4]
4->1 3 [4; 2; 1]
4->2 -1 [4; 2]
4->3 1 [4; 2; 1; 3]
</pre>
</pre>


Line 1,639: Line 1,640:
4 -> 2 -1 4 -> 2
4 -> 2 -1 4 -> 2
4 -> 3 1 4 -> 2 -> 1 -> 3</pre>
4 -> 3 1 4 -> 2 -> 1 -> 3</pre>

=={{header|Perl 6}}==
{{works with|Rakudo|2016.12}}
{{trans|Ruby}}

<lang perl6>sub Floyd-Warshall (Int $n, @edge) {
my @dist = [0, |(Inf xx $n-1)], *.Array.rotate(-1) … !*[*-1];
my @next = [0 xx $n] xx $n;

for @edge -> ($u, $v, $w) {
@dist[$u-1;$v-1] = $w;
@next[$u-1;$v-1] = $v-1;
}

for [X] ^$n xx 3 -> ($k, $i, $j) {
if @dist[$i;$j] > my $sum = @dist[$i;$k] + @dist[$k;$j] {
@dist[$i;$j] = $sum;
@next[$i;$j] = @next[$i;$k];
}
}

say ' Pair Distance Path';
for [X] ^$n xx 2 -> ($i, $j){
next if $i == $j;
my @path = $i;
@path.push: @next[@path[*-1];$j] until @path[*-1] == $j;
printf("%d → %d %4d %s\n", $i+1, $j+1, @dist[$i;$j],
@path.map( *+1 ).join(' → '));
}
}

Floyd-Warshall(4, [[1, 3, -2], [2, 1, 4], [2, 3, 3], [3, 4, 2], [4, 2, -1]]);</lang>
{{out}}
<pre> Pair Distance Path
1 → 2 -1 1 → 3 → 4 → 2
1 → 3 -2 1 → 3
1 → 4 0 1 → 3 → 4
2 → 1 4 2 → 1
2 → 3 2 2 → 1 → 3
2 → 4 4 2 → 1 → 3 → 4
3 → 1 5 3 → 4 → 2 → 1
3 → 2 1 3 → 4 → 2
3 → 4 2 3 → 4
4 → 1 3 4 → 2 → 1
4 → 2 -1 4 → 2
4 → 3 1 4 → 2 → 1 → 3
</pre>


=={{header|Phix}}==
=={{header|Phix}}==
Line 1,989: Line 1,943:
'(7 0 3 6)
'(7 0 3 6)
'(6 7)</pre>
'(6 7)</pre>

=={{header|Raku}}==
(formerly Perl 6)
{{works with|Rakudo|2016.12}}
{{trans|Ruby}}

<lang perl6>sub Floyd-Warshall (Int $n, @edge) {
my @dist = [0, |(Inf xx $n-1)], *.Array.rotate(-1) … !*[*-1];
my @next = [0 xx $n] xx $n;

for @edge -> ($u, $v, $w) {
@dist[$u-1;$v-1] = $w;
@next[$u-1;$v-1] = $v-1;
}

for [X] ^$n xx 3 -> ($k, $i, $j) {
if @dist[$i;$j] > my $sum = @dist[$i;$k] + @dist[$k;$j] {
@dist[$i;$j] = $sum;
@next[$i;$j] = @next[$i;$k];
}
}

say ' Pair Distance Path';
for [X] ^$n xx 2 -> ($i, $j){
next if $i == $j;
my @path = $i;
@path.push: @next[@path[*-1];$j] until @path[*-1] == $j;
printf("%d → %d %4d %s\n", $i+1, $j+1, @dist[$i;$j],
@path.map( *+1 ).join(' → '));
}
}

Floyd-Warshall(4, [[1, 3, -2], [2, 1, 4], [2, 3, 3], [3, 4, 2], [4, 2, -1]]);</lang>
{{out}}
<pre> Pair Distance Path
1 → 2 -1 1 → 3 → 4 → 2
1 → 3 -2 1 → 3
1 → 4 0 1 → 3 → 4
2 → 1 4 2 → 1
2 → 3 2 2 → 1 → 3
2 → 4 4 2 → 1 → 3 → 4
3 → 1 5 3 → 4 → 2 → 1
3 → 2 1 3 → 4 → 2
3 → 4 2 3 → 4
4 → 1 3 4 → 2 → 1
4 → 2 -1 4 → 2
4 → 3 1 4 → 2 → 1 → 3
</pre>


=={{header|REXX}}==
=={{header|REXX}}==