Thursday, 18 February 2016

Dijkstra's Algorithm using Min Heap to find shortest path from source to all other nodes in Java .....

here is the code .....


       
import java.io.BufferedReader;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.io.InputStreamReader;

public class DijkstraProblem {

 static int[][] costMatrix;
 static String line;
 static String[] lineValues;
 static int totalNodes;
 static int source;
 static int[] heapHolder; //to hold the cost of path to nodes 
 static int[] nodeNameHolder; //to hold the nodes corresponding to the heap cost in heapholder
 static int heapLength;
 static int smallest;
 static int left; // left child index
 static int right; // right child index
 static int temp;
 static int reducedNode = 0;
 static int reducedNodePathCost = 1;
 static int[] deletedNode; //to hold the cost and the node number everytime we delete root node from heap 
 static int newCostViaReducedNode;


 public static void main(String[] args) throws IOException {

  String path = "C:/Users/gauravy/Desktop/matrix.txt";
  loadfile(path);
  BufferedReader gr = new BufferedReader(new InputStreamReader(System.in));
  System.out.println("Please enter the node number from where you want shortest path to all nodes ...");
  source = Integer.parseInt(gr.readLine());
  applyDijkstra(source);

  System.out.println("Shortest path from source to all other nodes is below sequentially.....");
  for (int v = 0; v < totalNodes; v++) {
   System.out.print("source to node " + v + " cost is - " + costMatrix[source][v]);
   System.out.println("");
  }


 }

 // method to load the adjacency matrix for graph from the text file
 public static void loadfile(String path) throws IOException {

  FileReader fr = new FileReader(new File(path));
  BufferedReader br = new BufferedReader(fr);

  line = br.readLine();
  lineValues = line.split(" ");
  totalNodes = lineValues.length;
  costMatrix = new int[totalNodes][totalNodes];
  heapHolder = new int[totalNodes];
  deletedNode = new int[2];
  //viaNodeHolder = new int[totalNodes];
  nodeNameHolder = new int[totalNodes];
  heapLength = lineValues.length;

  int r = 0;

  while (line != null) {
   for (int c = 0; c < totalNodes; c++) {
    costMatrix[r][c] = Integer.parseInt(lineValues[c]);

   }
   r++;
   line = br.readLine();
   if (line != null)
    lineValues = line.split(" ");
  }
  fr.close();
  br.close();
 }

 // here we are applying the Dijkstra's algorithm
 public static void applyDijkstra(int source) {

  //viaNodeHolder[0] = 0;
  //nodeNameHolder[0]=0;
  for (int y = 0; y < heapLength; y++) {
   heapHolder[y] = Integer.MAX_VALUE;
   //viaNodeHolder[y] = 0;
   nodeNameHolder[y] = y;
  }
  heapHolder[source] = 0;

  buildMinHeap();

  for (int k = 0; k < totalNodes; k++) {
   deleteRoot();

   for (int p = 0; p < heapLength; p++) {
    newCostViaReducedNode = deletedNode[reducedNodePathCost] + costMatrix[deletedNode[reducedNode]][nodeNameHolder[p]];

    if (newCostViaReducedNode < heapHolder[p]) {
     heapHolder[p] = newCostViaReducedNode;
     costMatrix[source][nodeNameHolder[p]] = newCostViaReducedNode;
    }
    min_Heapify(0);
   }
  }
 }

 public static void buildMinHeap() {
  for (int p = heapHolder.length / 2 - 1; p >= 0; p--) {
   min_Heapify(p);
  }
 }

 // min heapify algorithm implemented here
 public static void min_Heapify(int p) {
  left = leftChild(p);
  right = rightChild(p);

  if ((left < heapLength) && (heapHolder[left] < heapHolder[p]))
   smallest = left;
  else
   smallest = p;

  if ((right < heapLength) && (heapHolder[right] < heapHolder[smallest]))
   smallest = right;

  if (smallest != p) {
   swap(smallest, p);
   min_Heapify(smallest);
  }
 }

 // returns index of left child
 public static int leftChild(int k) {
  return (2 * k + 1);
 }

 // returns of right child
 public static int rightChild(int i) {
  return (2 * i + 2);
 }

 // for swapping purpose
 public static void swap(int a, int b) {

  temp = heapHolder[a];
  heapHolder[a] = heapHolder[b];
  heapHolder[b] = temp;

  temp = nodeNameHolder[a];
  nodeNameHolder[a] = nodeNameHolder[b];
  nodeNameHolder[b] = temp;
 }

 // for deletion of root node from heap
 public static void deleteRoot() {

  deletedNode[reducedNode] = nodeNameHolder[0];
  deletedNode[reducedNodePathCost] = heapHolder[0];

  heapHolder[0] = heapHolder[heapLength - 1];
  //viaNodeHolder[0] = viaNodeHolder[heapLength - 1];
  nodeNameHolder[0] = nodeNameHolder[heapLength - 1];

  heapLength--;
  min_Heapify(0);
 }

}

       
 

1 comment: