TheAlgorithms-C-Plus-Plus/dynamic_programming/Floyd-Warshall.cpp

113 lines
2.3 KiB
C++
Raw Normal View History

2019-08-21 10:10:08 +08:00
#include <iostream>
#include <limits.h>
#include <string.h>
2017-10-12 19:53:14 +08:00
using namespace std;
//Wrapper class for storing a graph
2019-08-21 10:10:08 +08:00
class Graph
{
public:
2017-10-12 19:53:14 +08:00
int vertexNum;
2019-08-21 10:10:08 +08:00
int **edges;
2017-10-12 19:53:14 +08:00
//Constructs a graph with V vertices and E edges
2019-08-21 10:10:08 +08:00
Graph(int V)
{
2017-10-12 19:53:14 +08:00
this->vertexNum = V;
2019-08-21 10:10:08 +08:00
this->edges = (int **)malloc(V * sizeof(int *));
for (int i = 0; i < V; i++)
{
this->edges[i] = (int *)malloc(V * sizeof(int));
for (int j = 0; j < V; j++)
2017-10-12 19:53:14 +08:00
this->edges[i][j] = INT_MAX;
this->edges[i][i] = 0;
2019-08-21 10:10:08 +08:00
}
2017-10-12 19:53:14 +08:00
}
2019-08-21 10:10:08 +08:00
//Adds the given edge to the graph
void addEdge(int src, int dst, int weight)
{
2017-10-12 19:53:14 +08:00
this->edges[src][dst] = weight;
}
};
//Utility function to print distances
2019-08-21 10:10:08 +08:00
void print(int dist[], int V)
{
cout << "\nThe Distance matrix for Floyd - Warshall" << endl;
for (int i = 0; i < V; i++)
{
for (int j = 0; j < V; j++)
{
if (dist[i * V + j] != INT_MAX)
cout << dist[i * V + j] << "\t";
else
cout << "INF"
<< "\t";
2017-10-12 19:53:14 +08:00
}
2019-08-21 10:10:08 +08:00
cout << endl;
2017-10-12 19:53:14 +08:00
}
}
//The main function that finds the shortest path from a vertex
//to all other vertices using Floyd-Warshall Algorithm.
2019-08-21 10:10:08 +08:00
void FloydWarshall(Graph graph)
{
2017-10-12 19:53:14 +08:00
int V = graph.vertexNum;
int dist[V][V];
2019-08-21 10:10:08 +08:00
2017-10-12 19:53:14 +08:00
//Initialise distance array
2019-08-21 10:10:08 +08:00
for (int i = 0; i < V; i++)
for (int j = 0; j < V; j++)
dist[i][j] = graph.edges[i][j];
2017-10-12 19:53:14 +08:00
//Calculate distances
2019-08-21 10:10:08 +08:00
for (int k = 0; k < V; k++)
//Choose an intermediate vertex
2017-10-12 19:53:14 +08:00
2019-08-21 10:10:08 +08:00
for (int i = 0; i < V; i++)
//Choose a source vertex for given intermediate
2017-10-12 19:53:14 +08:00
2019-08-21 10:10:08 +08:00
for (int j = 0; j < V; j++)
//Choose a destination vertex for above source vertex
2017-10-12 19:53:14 +08:00
2019-08-21 10:10:08 +08:00
if (dist[i][k] != INT_MAX && dist[k][j] != INT_MAX && dist[i][k] + dist[k][j] < dist[i][j])
//If the distance through intermediate vertex is less than direct edge then update value in distance array
2017-10-12 19:53:14 +08:00
dist[i][j] = dist[i][k] + dist[k][j];
//Convert 2d array to 1d array for print
2019-08-21 10:10:08 +08:00
int dist1d[V * V];
for (int i = 0; i < V; i++)
for (int j = 0; j < V; j++)
dist1d[i * V + j] = dist[i][j];
print(dist1d, V);
}
2017-10-12 19:53:14 +08:00
//Driver Function
2019-08-21 10:10:08 +08:00
int main()
{
int V, E;
int src, dst, weight;
cout << "Enter number of vertices: ";
cin >> V;
cout << "Enter number of edges: ";
cin >> E;
2017-10-12 19:53:14 +08:00
Graph G(V);
2019-08-21 10:10:08 +08:00
for (int i = 0; i < E; i++)
{
cout << "\nEdge " << i + 1 << "\nEnter source: ";
cin >> src;
cout << "Enter destination: ";
cin >> dst;
cout << "Enter weight: ";
cin >> weight;
2017-10-12 19:53:14 +08:00
G.addEdge(src, dst, weight);
}
FloydWarshall(G);
return 0;
}