Given a directed graph, which may contain cycles, where every edge has weight, the task is to find the minimum cost of any simple path from a given source vertex ‘s’ to a given destination vertex ‘t’. Simple Path is the path from one vertex to another such that no vertex is visited more than once. If there is no simple path possible then return INF(infinite).
The graph is given as adjacency matrix representation where value of graph[i][j] indicates the weight of an edge from vertex i to vertex j and a value INF(infinite) indicates no edge from i to j.
Examples:
Input : V = 5, E = 6
s = 0, t = 2
graph[][] = 0 1 2 3 4
0 INF -1 INF 1 INF
1 INF INF -2 INF INF
2 -3 INF INF INF INF
3 INF INF -1 INF INF
4 INF INF INF 2 INF
Output : -3
Explanation :
The minimum cost simple path between 0 and 2 is given by:
0 -----> 1 ------> 2 whose cost is (-1) + (-2) = (-3).
Input : V = 5, E = 6
s = 0, t = 4
graph[][] = 0 1 2 3 4
0 INF -7 INF -2 INF
1 INF INF -11 INF INF
2 INF INF INF INF INF
3 INF INF INF 3 -4
4 INF INF INF INF INF
Output : -6
Explanation :
The minimum cost simple path between 0 and 2 is given by:
0 -----> 3 ------> 4 whose cost is (-2) + (-4) = (-6).
Approach :
The main idea to solve the above problem is to traverse through all simple paths from s to t using a modified version of Depth First Search and find the minimum cost path amongst them. One important observation about DFS is that it traverses one path at a time, hence we can traverse separate paths independently using DFS by marking the nodes as unvisited before leaving them.
A simple solution is to start from s, go to all adjacent vertices, and follow recursion for further adjacent vertices until we reach the destination. This algorithm will work even when negative weight cycles or self-edges are present in the graph.
Below is the implementation of the above-mentioned approach:
C++
#include <bits/stdc++.h>
using namespace std;
#define V 5
#define INF INT_MAX
int minimumCostSimplePath( int u, int destination,
bool visited[], int graph[][V])
{
if (u == destination)
return 0;
visited[u] = 1;
int ans = INF;
for ( int i = 0; i < V; i++) {
if (graph[u][i] != INF && !visited[i]) {
int curr = minimumCostSimplePath(i,
destination, visited, graph);
if (curr < INF) {
ans = min(ans, graph[u][i] + curr);
}
}
}
visited[u] = 0;
return ans;
}
int main()
{
int graph[V][V];
for ( int i = 0; i < V; i++) {
for ( int j = 0; j < V; j++) {
graph[i][j] = INF;
}
}
bool visited[V] = { 0 };
graph[0][1] = -1;
graph[0][3] = 1;
graph[1][2] = -2;
graph[2][0] = -3;
graph[3][2] = -1;
graph[4][3] = 2;
int s = 0, t = 2;
visited[s] = 1;
cout << minimumCostSimplePath(s, t,
visited, graph);
return 0;
}
|
Java
import java.util.*;
import java.lang.*;
class GFG{
static int V = 5 ;
static int INF = Integer.MAX_VALUE;
static int minimumCostSimplePath( int u, int destination,
boolean visited[],
int graph[][])
{
if (u == destination)
return 0 ;
visited[u] = true ;
int ans = INF;
for ( int i = 0 ; i < V; i++)
{
if (graph[u][i] != INF && !visited[i])
{
int curr = minimumCostSimplePath(i,
destination, visited, graph);
if (curr < INF)
{
ans = Math.min(ans, graph[u][i] + curr);
}
}
}
visited[u] = false ;
return ans;
}
public static void main(String[] args)
{
int graph[][] = new int [V][V];
for ( int i = 0 ; i < V; i++)
{
for ( int j = 0 ; j < V; j++)
{
graph[i][j] = INF;
}
}
boolean visited[] = new boolean [V];
graph[ 0 ][ 1 ] = - 1 ;
graph[ 0 ][ 3 ] = 1 ;
graph[ 1 ][ 2 ] = - 2 ;
graph[ 2 ][ 0 ] = - 3 ;
graph[ 3 ][ 2 ] = - 1 ;
graph[ 4 ][ 3 ] = 2 ;
int s = 0 , t = 2 ;
visited[s] = true ;
System.out.println(minimumCostSimplePath(s, t,
visited, graph));
}
}
|
Python3
import sys
V = 5
INF = sys.maxsize
def minimumCostSimplePath(u, destination,
visited, graph):
if (u = = destination):
return 0
visited[u] = 1
ans = INF
for i in range (V):
if (graph[u][i] ! = INF and not visited[i]):
curr = minimumCostSimplePath(i, destination,
visited, graph)
if (curr < INF):
ans = min (ans, graph[u][i] + curr)
visited[u] = 0
return ans
if __name__ = = "__main__" :
graph = [[INF for j in range (V)]
for i in range (V)]
visited = [ 0 for i in range (V)]
graph[ 0 ][ 1 ] = - 1
graph[ 0 ][ 3 ] = 1
graph[ 1 ][ 2 ] = - 2
graph[ 2 ][ 0 ] = - 3
graph[ 3 ][ 2 ] = - 1
graph[ 4 ][ 3 ] = 2
s = 0
t = 2
visited[s] = 1
print (minimumCostSimplePath(s, t, visited, graph))
|
C#
using System;
using System.Collections;
using System.Collections.Generic;
class GFG
{
static int V = 5;
static int INF = int .MaxValue;
static int minimumCostSimplePath( int u, int destination,
bool [] visited, int [, ] graph)
{
if (u == destination)
return 0;
visited[u] = true ;
int ans = INF;
for ( int i = 0; i < V; i++)
{
if (graph[u, i] != INF && !visited[i])
{
int curr = minimumCostSimplePath(i, destination,
visited, graph);
if (curr < INF)
{
ans = Math.Min(ans, graph[u, i] + curr);
}
}
}
visited[u] = false ;
return ans;
}
public static void Main( string [] args)
{
int [, ] graph = new int [V, V];
for ( int i = 0; i < V; i++)
{
for ( int j = 0; j < V; j++)
{
graph[i, j] = INF;
}
}
bool [] visited = new bool [V];
graph[0, 1] = -1;
graph[0, 3] = 1;
graph[1, 2] = -2;
graph[2, 0] = -3;
graph[3, 2] = -1;
graph[4, 3] = 2;
int s = 0, t = 2;
visited[s] = true ;
Console.WriteLine(minimumCostSimplePath(s, t, visited, graph));
}
}
|
Javascript
<script>
let V = 5
let INF = Number.MAX_SAFE_INTEGER
function minimumCostSimplePath(u, destination, visited, graph)
{
if (u == destination)
return 0;
visited[u] = 1;
let ans = INF;
for (let i = 0; i < V; i++) {
if (graph[u][i] != INF && !visited[i]) {
let curr = minimumCostSimplePath(i,
destination, visited, graph);
if (curr < INF) {
ans = Math.min(ans, graph[u][i] + curr);
}
}
}
visited[u] = 0;
return ans;
}
let graph = new Array();
for (let i = 0; i< V; i++){
graph.push([])
}
for (let i = 0; i < V; i++) {
for (let j = 0; j < V; j++) {
graph[i][j] = INF;
}
}
let visited = new Array(V).fill(0);
graph[0][1] = -1;
graph[0][3] = 1;
graph[1][2] = -2;
graph[2][0] = -3;
graph[3][2] = -1;
graph[4][3] = 2;
let s = 0, t = 2;
visited[s] = 1;
document.write(minimumCostSimplePath(s, t, visited, graph));
</script>
|
Time Complexity: O(V^2)
Auxiliary Space: O(V), since we are using an array of size V to store the visited nodes.
Feeling lost in the world of random DSA topics, wasting time without progress? It's time for a change! Join our DSA course, where we'll guide you on an exciting journey to master DSA efficiently and on schedule.
Ready to dive in? Explore our Free Demo Content and join our DSA course, trusted by over 100,000 geeks!
Last Updated :
21 Dec, 2022
Like Article
Save Article