Implemented step 2

Now createFastestPath and createShortestPath are created. Step 2
finished
This commit is contained in:
Adrien Barbanson 2021-04-02 09:05:16 +02:00
parent 9a32897b95
commit 8eeb871b1a

View file

@ -18,231 +18,340 @@ import java.util.List;
*/ */
public class Path { public class Path {
/** /**
* Create a new path that goes through the given list of nodes (in order), * Create a new path that goes through the given list of nodes (in order),
* choosing the fastest route if multiple are available. * choosing the fastest route if multiple are available.
* *
* @param graph Graph containing the nodes in the list. * @param graph Graph containing the nodes in the list.
* @param nodes List of nodes to build the path. * @param nodes List of nodes to build the path.
* *
* @return A path that goes through the given list of nodes. * @return A path that goes through the given list of nodes.
* *
* @throws IllegalArgumentException If the list of nodes is not valid, i.e. two * @throws IllegalArgumentException If the list of nodes is not valid, i.e. two
* consecutive nodes in the list are not connected in the graph. * consecutive nodes in the list are not connected in the graph.
* *
* @deprecated Need to be implemented. */
*/ public static Path createFastestPathFromNodes(Graph graph, List<Node> nodes)
public static Path createFastestPathFromNodes(Graph graph, List<Node> nodes) throws IllegalArgumentException {
throws IllegalArgumentException { int nodeListSize = nodes.size();
List<Arc> arcs = new ArrayList<Arc>();
// TODO:
return new Path(graph, arcs);
}
/** List<Arc> arcs = new ArrayList<Arc>(nodeListSize);
* Create a new path that goes through the given list of nodes (in order),
* choosing the shortest route if multiple are available.
*
* @param graph Graph containing the nodes in the list.
* @param nodes List of nodes to build the path.
*
* @return A path that goes through the given list of nodes.
*
* @throws IllegalArgumentException If the list of nodes is not valid, i.e. two
* consecutive nodes in the list are not connected in the graph.
*
* @deprecated Need to be implemented.
*/
public static Path createShortestPathFromNodes(Graph graph, List<Node> nodes)
throws IllegalArgumentException {
List<Arc> arcs = new ArrayList<Arc>();
// TODO:
return new Path(graph, arcs);
}
/** if(nodeListSize > 1) {
* Concatenate the given paths. //nodes.size() - 1 because we look at i and i+1
* for(int i=0;i<nodes.size() - 1;i++) {
* @param paths Array of paths to concatenate.
*
* @return Concatenated path.
*
* @throws IllegalArgumentException if the paths cannot be concatenated (IDs of
* map do not match, or the end of a path is not the beginning of the
* next).
*/
public static Path concatenate(Path... paths) throws IllegalArgumentException {
if (paths.length == 0) {
throw new IllegalArgumentException("Cannot concatenate an empty list of paths.");
}
final String mapId = paths[0].getGraph().getMapId();
for (int i = 1; i < paths.length; ++i) {
if (!paths[i].getGraph().getMapId().equals(mapId)) {
throw new IllegalArgumentException(
"Cannot concatenate paths from different graphs.");
}
}
ArrayList<Arc> arcs = new ArrayList<>();
for (Path path: paths) {
arcs.addAll(path.getArcs());
}
Path path = new Path(paths[0].getGraph(), arcs);
if (!path.isValid()) {
throw new IllegalArgumentException(
"Cannot concatenate paths that do not form a single path.");
}
return path;
}
// Graph containing this path. //for each node we try to find fastestPath between i and i+1
private final Graph graph; List<Arc> neighbourhood = nodes.get(i).getSuccessors();
// Origin of the path Arc fastestPath = null;
private final Node origin;
// List of arcs in this path. for(Arc nextArc : neighbourhood) {
private final List<Arc> arcs; if(nextArc.getDestination().compareTo(nodes.get(i+1)) == 0) {
//here we find a path between i and i+1, now we need to see if it's the fastest one
if(fastestPath == null) {
fastestPath = nextArc;
}
else if(fastestPath.getMinimumTravelTime() > nextArc.getMinimumTravelTime()) {
fastestPath = nextArc;
}
}
}
/** if(fastestPath == null) {
* Create an empty path corresponding to the given graph. throw new IllegalArgumentException();
* }
* @param graph Graph containing the path.
*/
public Path(Graph graph) {
this.graph = graph;
this.origin = null;
this.arcs = new ArrayList<>();
}
/** arcs.add(fastestPath);
* Create a new path containing a single node. }
* }
* @param graph Graph containing the path. else if (nodeListSize == 1) {
* @param node Single node of the path. return new Path(graph, nodes.get(0));
*/ }
public Path(Graph graph, Node node) { else {
this.graph = graph; //nodeListSize == 0
this.origin = node; return new Path(graph);
this.arcs = new ArrayList<>(); }
}
/** return new Path(graph, arcs);
* Create a new path with the given list of arcs. }
*
* @param graph Graph containing the path.
* @param arcs Arcs to construct the path.
*/
public Path(Graph graph, List<Arc> arcs) {
this.graph = graph;
this.arcs = arcs;
this.origin = arcs.size() > 0 ? arcs.get(0).getOrigin() : null;
}
/** /**
* @return Graph containing the path. * Create a new path that goes through the given list of nodes (in order),
*/ * choosing the shortest route if multiple are available.
public Graph getGraph() { *
return graph; * @param graph Graph containing the nodes in the list.
} * @param nodes List of nodes to build the path.
*
* @return A path that goes through the given list of nodes.
*
* @throws IllegalArgumentException If the list of nodes is not valid, i.e. two
* consecutive nodes in the list are not connected in the graph.
*
*
*/
public static Path createShortestPathFromNodes(Graph graph, List<Node> nodes)
throws IllegalArgumentException {
/** int nodeListSize = nodes.size();
* @return First node of the path.
*/
public Node getOrigin() {
return origin;
}
/** List<Arc> arcs = new ArrayList<Arc>(nodeListSize);
* @return Last node of the path.
*/
public Node getDestination() {
return arcs.get(arcs.size() - 1).getDestination();
}
/** if(nodeListSize > 1) {
* @return List of arcs in the path. //nodes.size() - 1 because we look at i and i+1
*/ for(int i=0;i<nodes.size() - 1;i++) {
public List<Arc> getArcs() {
return Collections.unmodifiableList(arcs);
}
/** //for each node we try to find shortestPath between i and i+1
* Check if this path is empty (it does not contain any node). List<Arc> neighbourhood = nodes.get(i).getSuccessors();
*
* @return true if this path is empty, false otherwise.
*/
public boolean isEmpty() {
return this.origin == null;
}
/** Arc shortestPath = null;
* Get the number of <b>nodes</b> in this path.
*
* @return Number of nodes in this path.
*/
public int size() {
return isEmpty() ? 0 : 1 + this.arcs.size();
}
/** for(Arc nextArc : neighbourhood) {
* Check if this path is valid. if(nextArc.getDestination().compareTo(nodes.get(i+1)) == 0) {
* //here we find a path between i and i+1, now we need to see if it's the shortest one
* A path is valid if any of the following is true: if(shortestPath == null) {
* <ul> shortestPath = nextArc;
* <li>it is empty;</li> }
* <li>it contains a single node (without arcs);</li> else if(shortestPath.getLength() > nextArc.getLength()) {
* <li>the first arc has for origin the origin of the path and, for two shortestPath = nextArc;
* consecutive arcs, the destination of the first one is the origin of the }
* second one.</li> }
* </ul> }
*
* @return true if the path is valid, false otherwise.
*
* @deprecated Need to be implemented.
*/
public boolean isValid() {
// TODO:
return false;
}
/** if(shortestPath == null) {
* Compute the length of this path (in meters). throw new IllegalArgumentException();
* }
* @return Total length of the path (in meters).
*
* @deprecated Need to be implemented.
*/
public float getLength() {
// TODO:
return 0;
}
/** arcs.add(shortestPath);
* Compute the time required to travel this path if moving at the given speed. }
* }
* @param speed Speed to compute the travel time. else if (nodeListSize == 1) {
* return new Path(graph, nodes.get(0));
* @return Time (in seconds) required to travel this path at the given speed (in }
* kilometers-per-hour). else {
* //nodeListSize == 0
* @deprecated Need to be implemented. return new Path(graph);
*/ }
public double getTravelTime(double speed) {
// TODO:
return 0;
}
/** return new Path(graph, arcs);
* Compute the time to travel this path if moving at the maximum allowed speed }
* on every arc.
* /**
* @return Minimum travel time to travel this path (in seconds). * Concatenate the given paths.
* *
* @deprecated Need to be implemented. * @param paths Array of paths to concatenate.
*/ *
public double getMinimumTravelTime() { * @return Concatenated path.
// TODO: *
return 0; * @throws IllegalArgumentException if the paths cannot be concatenated (IDs of
} * map do not match, or the end of a path is not the beginning of the
* next).
*/
public static Path concatenate(Path... paths) throws IllegalArgumentException {
if (paths.length == 0) {
throw new IllegalArgumentException("Cannot concatenate an empty list of paths.");
}
final String mapId = paths[0].getGraph().getMapId();
for (int i = 1; i < paths.length; ++i) {
if (!paths[i].getGraph().getMapId().equals(mapId)) {
throw new IllegalArgumentException(
"Cannot concatenate paths from different graphs.");
}
}
ArrayList<Arc> arcs = new ArrayList<>();
for (Path path: paths) {
arcs.addAll(path.getArcs());
}
Path path = new Path(paths[0].getGraph(), arcs);
if (!path.isValid()) {
throw new IllegalArgumentException(
"Cannot concatenate paths that do not form a single path.");
}
return path;
}
// Graph containing this path.
private final Graph graph;
// Origin of the path
private final Node origin;
// List of arcs in this path.
private final List<Arc> arcs;
/**
* Create an empty path corresponding to the given graph.
*
* @param graph Graph containing the path.
*/
public Path(Graph graph) {
this.graph = graph;
this.origin = null;
this.arcs = new ArrayList<>();
}
/**
* Create a new path containing a single node.
*
* @param graph Graph containing the path.
* @param node Single node of the path.
*/
public Path(Graph graph, Node node) {
this.graph = graph;
this.origin = node;
this.arcs = new ArrayList<>();
}
/**
* Create a new path with the given list of arcs.
*
* @param graph Graph containing the path.
* @param arcs Arcs to construct the path.
*/
public Path(Graph graph, List<Arc> arcs) {
this.graph = graph;
this.arcs = arcs;
this.origin = arcs.size() > 0 ? arcs.get(0).getOrigin() : null;
}
/**
* @return Graph containing the path.
*/
public Graph getGraph() {
return graph;
}
/**
* @return First node of the path.
*/
public Node getOrigin() {
return origin;
}
/**
* @return Last node of the path.
*/
public Node getDestination() {
return arcs.get(arcs.size() - 1).getDestination();
}
/**
* @return List of arcs in the path.
*/
public List<Arc> getArcs() {
return Collections.unmodifiableList(arcs);
}
/**
* Check if this path is empty (it does not contain any node).
*
* @return true if this path is empty, false otherwise.
*/
public boolean isEmpty() {
return this.origin == null;
}
/**
* Get the number of <b>nodes</b> in this path.
*
* @return Number of nodes in this path.
*/
public int size() {
return isEmpty() ? 0 : 1 + this.arcs.size();
}
/**
* Check if this path is valid.
*
* A path is valid if any of the following is true:
* <ul>
* <li>it is empty;</li>
* <li>it contains a single node (without arcs);</li>
* <li>the first arc has for origin the origin of the path and, for two
* consecutive arcs, the destination of the first one is the origin of the
* second one.</li>
* </ul>
*
* @return true if the path is valid, false otherwise.
*
*/
public boolean isValid() {
if((this.isEmpty() && arcs.isEmpty()) || this.size() == 1) {
return true;
}
//the first arc has for origin the origin of the path
if(this.arcs.get(0).getOrigin() != this.origin) {
return false;
}
//for two consecutive arcs, the destination of the first one is the origin of the second one
for(int i = 0 ; i < arcs.size() - 1 ;i++) {
if(arcs.get(i).getDestination().compareTo(arcs.get(i+1).getOrigin()) != 0) {
return false;
}
}
return true;
}
/**
* Compute the length of this path (in meters).
*
* @return Total length of the path (in meters).
*
*/
public float getLength() {
float totalLength = 0.0f;
for(Arc arc : arcs) {
totalLength += arc.getLength();
}
return totalLength;
}
/**
* Compute the time required to travel this path if moving at the given speed.
*
* @param speed Speed to compute the travel time.
*
* @return Time (in seconds) required to travel this path at the given speed (in
* kilometers-per-hour).
*
*
*/
public double getTravelTime(double speed) {
double totalTime = 0.0d;
for(Arc arc : arcs) {
totalTime += arc.getTravelTime(speed);
}
return totalTime;
}
/**
* Compute the time to travel this path if moving at the maximum allowed speed
* on every arc.
*
* @return Minimum travel time to travel this path (in seconds).
*
*
*/
public double getMinimumTravelTime() {
double totalTime = 0.0d;
for(Arc arc : arcs) {
totalTime += arc.getMinimumTravelTime();
}
return totalTime;
}
} }