dijkstra: functional
This commit is contained in:
parent
6e4c4de7dd
commit
26e5d5dac9
1 changed files with 73 additions and 50 deletions
|
@ -1,7 +1,6 @@
|
||||||
package org.insa.graphs.algorithm.shortestpath;
|
package org.insa.graphs.algorithm.shortestpath;
|
||||||
|
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Arrays;
|
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
|
||||||
import org.insa.graphs.algorithm.AbstractSolution.Status;
|
import org.insa.graphs.algorithm.AbstractSolution.Status;
|
||||||
|
@ -23,47 +22,50 @@ public class DijkstraAlgorithm extends ShortestPathAlgorithm {
|
||||||
ShortestPathSolution solution = null;
|
ShortestPathSolution solution = null;
|
||||||
// TODO:
|
// TODO:
|
||||||
|
|
||||||
// Heap of "sommets"
|
// List of sommets, but with type Label
|
||||||
BinaryHeap<Label> labels = new BinaryHeap<Label>(); // change to a comparable type
|
ArrayList<Label> labels = new ArrayList<Label>();
|
||||||
|
// Heap of sommets
|
||||||
|
BinaryHeap<Label> tas = new BinaryHeap<Label>();
|
||||||
|
|
||||||
Graph graph = data.getGraph();
|
Graph graph = data.getGraph();
|
||||||
final int nbNodes = graph.size();
|
final int nbNodes = graph.size();
|
||||||
|
|
||||||
// Initialize array of distances.
|
|
||||||
double[] distances = new double[nbNodes];
|
|
||||||
Arrays.fill(distances, Double.POSITIVE_INFINITY);
|
|
||||||
distances[data.getOrigin().getId()] = 0;
|
|
||||||
|
|
||||||
// Notify observers about the first event (origin processed).
|
// Notify observers about the first event (origin processed).
|
||||||
notifyOriginProcessed(data.getOrigin());
|
notifyOriginProcessed(data.getOrigin());
|
||||||
|
|
||||||
// Init Dijkstra
|
// Init Dijkstra
|
||||||
//ArrayList<Label> labels = new ArrayList<Label>();
|
|
||||||
for (Node node : graph.getNodes()) {
|
for (Node node : graph.getNodes()) {
|
||||||
labels.insert(new Label(node));
|
labels.add(new Label(node));
|
||||||
}
|
}
|
||||||
// Nodes set
|
|
||||||
for (Label label : labels.array) {
|
|
||||||
label.marked = false;
|
|
||||||
label.setPathCost(Float.MAX_VALUE);
|
|
||||||
label.parentNode = null;
|
|
||||||
}
|
|
||||||
// Origin set
|
|
||||||
Label s = labels.array.get(0);
|
|
||||||
s.setPathCost(0);
|
|
||||||
labels.insert(s);
|
|
||||||
|
|
||||||
boolean trouve = false; // TODO : breaking condition
|
Label s = new Label(data.getOrigin());
|
||||||
|
|
||||||
|
// Add origin in the heap
|
||||||
|
//Label s = origin;//labels.get(0);
|
||||||
|
s.setPathCost(0);
|
||||||
|
tas.insert(s);
|
||||||
|
|
||||||
|
// On considère le sommet x à chaque itération
|
||||||
Label x;
|
Label x;
|
||||||
while (!labels.isEmpty() && !trouve) {
|
|
||||||
x = labels.deleteMin();
|
while (!tas.isEmpty()) {
|
||||||
|
x = tas.deleteMin();
|
||||||
x.mark();
|
x.mark();
|
||||||
|
|
||||||
// y shall be all the successors of x
|
// A marked node is considered as reached
|
||||||
|
notifyNodeReached(x.getNode());
|
||||||
|
|
||||||
|
// We create a list of node successors of x, instead of a list of Arcs.
|
||||||
float arc_cost = 0;
|
float arc_cost = 0;
|
||||||
for (Label y : labels.array) {
|
ArrayList<Node> successors = new ArrayList<Node>();
|
||||||
if (y.getParentNode() == x.getNode()) {
|
for (Arc k : x.getNode().getSuccessors()) {
|
||||||
if (y.isMarked()) {
|
successors.add(k.getDestination());
|
||||||
|
}
|
||||||
|
|
||||||
|
// We loop only on the successors of the node with this for and if.
|
||||||
|
for (Label y : labels) {
|
||||||
|
if (successors.contains(y.getNode())) {
|
||||||
|
if (!y.isMarked()) {
|
||||||
// This loop serves to get the lentgh of the arc as
|
// This loop serves to get the lentgh of the arc as
|
||||||
// we know its origin and destination
|
// we know its origin and destination
|
||||||
for (Arc arc : x.getNode().getSuccessors()) {
|
for (Arc arc : x.getNode().getSuccessors()) {
|
||||||
|
@ -71,11 +73,21 @@ public class DijkstraAlgorithm extends ShortestPathAlgorithm {
|
||||||
arc_cost = arc.getLength();
|
arc_cost = arc.getLength();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
float new_cost = x.getCost() + arc_cost;
|
float possible_path_cost = x.getCost() + arc_cost;
|
||||||
if (y.getCost() > new_cost) {
|
if (y.getCost() > possible_path_cost) {
|
||||||
y.setPathCost(new_cost);
|
// Mise à jour du label
|
||||||
labels.insert(y);
|
y.setPathCost(possible_path_cost);
|
||||||
y.setParentNode(x.getNode());
|
y.setParentNode(x.getNode());
|
||||||
|
// Si y est déjà dans le tas, on va l'update, pas l'insérer
|
||||||
|
// On a pas de fonction update donc on fait un remove puis insert
|
||||||
|
if (tas.array.contains(y)){
|
||||||
|
tas.remove(y);
|
||||||
|
tas.insert(y);
|
||||||
|
}
|
||||||
|
// il n'y est pas déjà on l'insère
|
||||||
|
else {
|
||||||
|
tas.insert(y);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -84,27 +96,34 @@ public class DijkstraAlgorithm extends ShortestPathAlgorithm {
|
||||||
|
|
||||||
// Create the path ...
|
// Create the path ...
|
||||||
ArrayList<Arc> arcs_path = new ArrayList<>();
|
ArrayList<Arc> arcs_path = new ArrayList<>();
|
||||||
Label dest = labels.findMin();
|
|
||||||
for (Label label : labels.array) {
|
|
||||||
if (label.getNode() == data.getDestination()){
|
|
||||||
dest = label;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
Node current = dest.getParentNode();
|
// We will find the path using the parent nodes, from the destination to the origin
|
||||||
while (current != null) {
|
Node current_node = data.getDestination();
|
||||||
for (Arc arc : current.getSuccessors()) {
|
Label current_label = new Label(current_node);
|
||||||
if (arc.getDestination() == dest.getNode()) {
|
System.out.println(current_node.getId());
|
||||||
arcs_path.add(arc);
|
|
||||||
|
while (current_node != null && current_node != data.getOrigin()) {
|
||||||
|
// Find the label matching the parent node
|
||||||
|
for (Label label : labels) {
|
||||||
|
if (label.getNode() == current_node){
|
||||||
|
current_label = label;
|
||||||
|
current_node = current_label.getParentNode();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for (Label label : labels.array) {
|
// Knowing the parent node, get the arc between the parent and
|
||||||
if (label.getNode() == current){
|
// current node and add it to the path
|
||||||
dest = label;
|
if (current_node != null){
|
||||||
current = label.getParentNode();
|
for (Arc arc : current_node.getSuccessors()) {
|
||||||
|
if (arc.getDestination().getId() == current_label.getNode().getId() ) {
|
||||||
|
arcs_path.add(arc);
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
notifyDestinationReached(data.getDestination());
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
// Reverse the path...
|
// Reverse the path...
|
||||||
Collections.reverse(arcs_path);
|
Collections.reverse(arcs_path);
|
||||||
|
@ -112,6 +131,10 @@ public class DijkstraAlgorithm extends ShortestPathAlgorithm {
|
||||||
// Create the final solution.
|
// Create the final solution.
|
||||||
solution = new ShortestPathSolution(data, Status.OPTIMAL, new Path(graph, arcs_path));
|
solution = new ShortestPathSolution(data, Status.OPTIMAL, new Path(graph, arcs_path));
|
||||||
|
|
||||||
|
/*System.out.println("watch here" + "\n");
|
||||||
|
for (Arc a : arcs_path){
|
||||||
|
System.out.println(a.getOrigin().getId() + " --- " + a.getDestination().getId() + "\n");
|
||||||
|
}*/
|
||||||
return solution;
|
return solution;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue