ppt

advertisement
“The shortest-path algorithms are all single-source algorithms, which begin at
some starting point and compute the shortest paths from it to all vertices.” Weiss
ALG0183 Algorithms & Data Structures
Lecture 19
The basics of Graph.java (code by Weiss)
Weiss, Chapter 14
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
1
What does Graph.java do?
• The user specifies a graph in a text file.
• Graph.java reads the text file and builds up an internal
representation of the graph.
• The user enters start and destination nodes.
• The user specifies which algorithm should be executed
to find the shortest path:
–
–
–
–
u unweighted (breadth-first search algorithm)
d only positive weights on edges (Dijkstra´s algorithm)
n negative weights present (Bellman-Ford algorithm)
a acyclic with neg. weights (topological sort algorithm)
• Graph.java reports the shortest path (or an exception in
the event of an error).
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
2
sample input file “graph1.txt”
Figure 14.5 Weiss ©Addison Wesley
The input is a list of edges, one per line.
Graph.java does not know the names of the vertices, nor how many
vertices and edges there are: it reads the input file to find out.
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
3
sample I/O for graph1.txt
File read...
5 vertices
Enter start node:A
Enter destination node:D
Enter algorithm (u, d, n, a ): u unweighted
(Cost is: 1.0) A to D
Enter start node:A
Enter destination node:D
Enter algorithm (u, d, n, a ): d Dijkstra (positive)
(Cost is: 66.0) A to B to E to D
(Cost is: 66.0) A to B to E to D
Enter start node:A
Enter destination node:D
Enter algorithm (u, d, n, a ): n Bellman-Ford (with negative)
(Cost is: 66.0) A to B to E to D
Enter start node:A
Enter destination node:D
Enter algorithm (u, d, n, a ): a acyclic (topological sort)
Enter start node:gr.GraphException: Graph has a cycle!
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
4
try {
System.out.print( "Enter start node:" );
if( ( startName = in.readLine( ) ) == null ) return false;
System.out.print( "Enter destination node:" );
if( ( destName = in.readLine( ) ) == null ) return false;
System.out.print( " Enter algorithm (u, d, n, a ): " );
if( ( alg = in.readLine( ) ) == null ) return false;
if( alg.equals( "u" ) )
u unweighted
g.unweighted( startName );
else if( alg.equals( "d" ) ) {
d Dijkstra (positive)
g.dijkstra( startName );
g.printPath( destName );
//
g.dijkstra2( startName );
}
else if( alg.equals( "n" ) )
n Bellman-Ford (with negative)
g.negative( startName );
else if( alg.equals( "a" ) )
a acyclic (topological sort)
g.acyclic( startName );
g.printPath( destName );
}
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
5
Graph g = new Graph( );
try {
FileReader fin = new FileReader(args[0]);
BufferedReader graphFile = new BufferedReader( fin );
// Read the edges and insert
String line;
while( ( line = graphFile.readLine( ) ) != null ) {
StringTokenizer st = new StringTokenizer( line );
try {
if( st.countTokens( ) != 3 )
{
System.err.println( "Skipping ill-formatted line " + line );
continue;
}
String source = st.nextToken( );
String dest = st.nextToken( );
int cost = Integer.parseInt( st.nextToken( ) );
g.addEdge( source, dest, cost );
}
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
6
Some imports in Graph.java
import java.io.FileReader;
import java.io.InputStreamReader;
import java.io.BufferedReader;
import java.io.IOException;
import java.util.StringTokenizer;
//import java.util.Iterator;
import java.util.Collection;
import java.util.List;
import java.util.Queue;
import java.util.Map;
import java.util.LinkedList;
import java.util.HashMap;
import java.util.NoSuchElementException;
import java.util.PriorityQueue;
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
7
The beginning of the Graph class
public class Graph
{
public static final double INFINITY = Double.MAX_VALUE;
private Map<String,Vertex> vertexMap = new HashMap<String,Vertex>( );
• According to the Java API, Double.MAX_VALUE is
“A constant holding the largest positive finite
value of type double, (2-2-52)·21023.”
– i.e. 1.7976931348623157E308
• The cost of reaching a vertex is initially set to
INFINITY.
else if( w.dist == INFINITY )
System.out.println( destName + " is unreachable" );
See later: code in method printPath.
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
8
key
value
What is a HashMap?
•
•
•
•
•
•
HashMap implements the Map interface.
An entry in a map has a key and a value.
Duplicate keys are not allowed.
A key can be an instance of any class.
A value can be an instance of any class.
To retrieve a value associated with a key, the map´s get
method is called.
– The key is the index into a map collection.
• There is no guarantee of the order of entries in a HashMap.
• The type for the key and value must be specified when
declaring and creating a map.
private Map<String,Vertex> vertexMap = new HashMap<String,Vertex>( );
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
9
Hash table @ Wikipedia
27.10.2009
“In computer science, a hash table or hash map is a data structure
that uses a hash function to efficiently map certain identifiers or
keys (e.g., person names) to associated values (e.g., their telephone
numbers). The hash function is used to transform the key into the
index (the hash) of an array element (the slot or bucket) where the
corresponding value is to be sought.”
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
10
HashMap @ Java API
http://java.sun.com/javase/6/docs/api/
• “This implementation provides constant-time performance
for the basic operations (get and put), assuming the hash
function disperses the elements properly among the
buckets.”
• “The capacity is the number of buckets in the hash table,
and the initial capacity is simply the capacity at the time
the hash table is created. The load factor is a measure of
how full the hash table is allowed to get before its capacity
is automatically increased. When the number of entries in
the hash table exceeds the product of the load factor and
the current capacity, the hash table is rehashed (that is,
internal data structures are rebuilt) so that the hash table
has approximately twice the number of buckets.”
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
11
// Represents a vertex in the graph.
class Vertex
{
public String name; // Vertex name
the vertex name never changes
public List<Edge> adj; // Adjacent vertices
the list of edges never changes
public double dist; // Cost
from the starting vertex to this vertex
public Vertex prev; // Previous vertex on shortest path
public int
scratch;// Extra variable used in algorithm
public Vertex( String nm )
the constructor
{ name = nm; adj = new LinkedList<Edge>( ); reset( ); }
public void reset( )
initialization
{ dist = Graph.INFINITY; prev = null; scratch = 0; }
//{ dist = Graph.INFINITY; prev = null; pos = null; scratch = 0; }
// public PairingHeap.Position<Path> pos; // Used for dijkstra2 (Chapter 23)
}
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
12
cost
destination
// Represents an edge in the graph.
class Edge
{
public Vertex dest; // Second vertex in Edge
public double cost; // Edge cost
public Edge( Vertex d, double c )
{
dest = d;
cost = c;
}
the destination
weight
the constructor
}
Edges are stored in an adjacency list.
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
13
/**
* Add a new edge to the graph.
*/
public void addEdge( String sourceName, String destName, double cost )
{
Vertex v = getVertex( sourceName );
Vertex w = getVertex( destName );
v.adj.add( new Edge( w, cost ) );
}
g.addEdge( source, dest, cost );
See earlier: code in method main.
Note that the method getVertex can also create the object if
necessary: it is not a simple get method.
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
14
/**
* If vertexName is not present, add it to vertexMap.
* In either case, return the Vertex.
*/
private Vertex getVertex( String vertexName )
{
Vertex v = vertexMap.get( vertexName );
get the vertex from the map
if( v == null )
but if the vertex does not exist
{
v = new Vertex( vertexName );
create a new vertex and…
vertexMap.put( vertexName, v );
…put it in the map
}
return v;
}
“The getVertex routine returns the Vertex objetc that represents vertexName, creating
the object if it needs to do.” Weiss
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
15
/**
* Initializes the vertex output info prior to running
* any shortest path algorithm.
*/
private void clearAll( )
{
for( Vertex v : vertexMap.values( ) ) values() returns a “Collection view”
v.reset( );
}
public void reset( )
{ dist = Graph.INFINITY; prev = null; scratch = 0; }
See earlier: code in class Vertex.
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
16
/**
* Driver routine to handle unreachables and print total cost.
* It calls recursive routine to print shortest path to
* destNode after a shortest path algorithm has run.
*/
public void printPath( String destName )
{
Vertex w = vertexMap.get( destName );
if( w == null )
throw new NoSuchElementException( "Destination vertex not found" );
else if( w.dist == INFINITY )
System.out.println( destName + " is unreachable" );
else
{
System.out.print( "(Cost is: " + w.dist + ") " );
printPath( w );
note that the argument references a vertex
System.out.println( );
}
}
ALG0183 Algorithms & Data Structures by
8/25/2009
17
Dr Andy Brooks
different signature
/**
* Recursive routine to print shortest path to dest
* after running shortest path algorithm. The path
* is known to exist.
*/
private void printPath( Vertex dest )
the argument references a vertex
{
if( dest.prev != null )
{
printPath( dest.prev );
System.out.print( " to " );
}
System.out.print( dest.name );
}
8/25/2009
ALG0183 Algorithms & Data Structures by
Dr Andy Brooks
18
Download