student start_code_U08223_cwk1 (1)/.DS_Store
__MACOSX/student start_code_U08223_cwk1 (1)/._.DS_Store
student start_code_U08223_cwk1 (1)/Connection.javastudent start_code_U08223_cwk1 (1)/Connection.java
package cwk1test;
/**
* Interface to be implemented by classes representing undirected connections
* between Stations in a Network
*
* N.B. You may change the package name for this interface, but you should
* not modify it in any other way.
*/
publicinterfaceConnection{
/**
* Get the distance value for this Connection
*
* @return distance value for the Connection
*/
double getDistance();
/**
* Get a reference to one of the stations that are linked by this Connection
* The returned Sation is different to that returned by getStationB()
*
* @return a reference to one of the Stations linked by this Connection
*/
Station getStationA();
/**
* Get a reference to one of the stations that are linked by this Connection
* The returned Sation is different to that returned by getStationA()
*
* @return a reference to one of the Stations linked by this Connection
*/
Station getStationB();
/**
* Given one of the stations linked by this Connection, return the other
*
* @param station one of the Stations linked by the Connection
* @return the other Station
* PRECONDITION: station==getStationA() || station==getStationB()
*/
Station getOtherStation(Station station);
}
__MACOSX/student start_code_U08223_cwk1 (1)/._Connection.java
student start_code_U08223_cwk1 (1)/GraphicsUtil.javastudent start_code_U08223_cwk1 (1)/GraphicsUtil.java/**
* Utility glass for drawing networks
*/
package cwk1test;
import java.awt.Color;
import java.awt.FontMetrics;
import java.awt.Graphics;
import javax.swing.JComponent;
/**
*
* @author p0073862
*/
publicclassGraphicsUtil{
privatestaticfinaldouble NOTIONAL_WIDTH =255;
privatestaticfinaldouble NOTIONAL_HEIGHT =255;
privatestaticfinalint CIRCLE_RADIUS =5;
privatestaticfinalint[] xPoints =newint[2];
privatestaticfinalint[] yPoints =newint[2];
/**
* Draw a network onto a component
*
*
* @param network Network to be drawn
* @param component Component on to which the network is to be drawn (e.g a
* JPanel)
* @param g Graphics object used for drawing
*/
publicstaticvoid drawNetwork(Network network,JComponent component,
Graphics g){
Color oldColor = g.getColor();
double xScale = component.getWidth()/ NOTIONAL_WIDTH;
double yScale = component.getHeight()/ NOTIONAL_HEIGHT;
for(Station station : network.getStations()){
FontMetrics metrics = g.getFontMetrics();
int textHeight = metrics.getHeight();
int x =(int)Math.round(xScale * station.getxPos())- CIRCLE_RADIUS;
int y =(int)Math.round(yScale * station.getyPos())- CIRCLE_RADIUS;
int diameter = CIRCLE_RADIUS *2;
g.setColor(Color.BLACK);
g.fillOval(x, y, diameter, diameter);
g.setColor(Color.RED).
1. student start_code_U08223_cwk1 (1)/.DS_Store
__MACOSX/student start_code_U08223_cwk1 (1)/._.DS_Store
student start_code_U08223_cwk1 (1)/Connection.javastudent
start_code_U08223_cwk1 (1)/Connection.java
package cwk1test;
/**
* Interface to be implemented by classes representing undirecte
d connections
* between Stations in a Network
*
* N.B. You may change the package name for this interface, bu
t you should
* not modify it in any other way.
*/
publicinterfaceConnection{
/**
* Get the distance value for this Connection
*
* @return distance value for the Connection
*/
double getDistance();
/**
* Get a reference to one of the stations that are linked by thi
s Connection
* The returned Sation is different to that returned by getStati
onB()
*
* @return a reference to one of the Stations linked by this C
2. onnection
*/
Station getStationA();
/**
* Get a reference to one of the stations that are linked by thi
s Connection
* The returned Sation is different to that returned by getStati
onA()
*
* @return a reference to one of the Stations linked by this C
onnection
*/
Station getStationB();
/**
* Given one of the stations linked by this Connection, return
the other
*
* @param station one of the Stations linked by the Connecti
on
* @return the other Station
* PRECONDITION: station==getStationA() || station==getSt
ationB()
*/
Station getOtherStation(Station station);
}
__MACOSX/student start_code_U08223_cwk1
(1)/._Connection.java
student start_code_U08223_cwk1 (1)/GraphicsUtil.javastudent
start_code_U08223_cwk1 (1)/GraphicsUtil.java/**
* Utility glass for drawing networks
3. */
package cwk1test;
import java.awt.Color;
import java.awt.FontMetrics;
import java.awt.Graphics;
import javax.swing.JComponent;
/**
*
* @author p0073862
*/
publicclassGraphicsUtil{
privatestaticfinaldouble NOTIONAL_WIDTH =255;
privatestaticfinaldouble NOTIONAL_HEIGHT =255;
privatestaticfinalint CIRCLE_RADIUS =5;
privatestaticfinalint[] xPoints =newint[2];
privatestaticfinalint[] yPoints =newint[2];
/**
* Draw a network onto a component
*
*
* @param network Network to be drawn
* @param component Component on to which the network is
to be drawn (e.g a
* JPanel)
* @param g Graphics object used for drawing
*/
publicstaticvoid drawNetwork(Network network,JComponent co
mponent,
Graphics g){
Color oldColor = g.getColor();
double xScale = component.getWidth()/ NOTIONAL_WIDTH;
4. double yScale = component.getHeight()/ NOTIONAL_HEIGHT;
for(Station station : network.getStations()){
FontMetrics metrics = g.getFontMetrics();
int textHeight = metrics.getHeight();
int x =(int)Math.round(xScale * station.getxPos())-
CIRCLE_RADIUS;
int y =(int)Math.round(yScale * station.getyPos())-
CIRCLE_RADIUS;
int diameter = CIRCLE_RADIUS *2;
g.setColor(Color.BLACK);
g.fillOval(x, y, diameter, diameter);
g.setColor(Color.RED);
g.drawString(station.getName(), x + CIRCLE_RADIUS,
y - CIRCLE_RADIUS);
for(Connection connection : network.getConnectionsFrom(statio
n)){
xPoints[0]=
(int)Math.round(xScale * connection.getStationA().getxPos());
xPoints[1]=
(int)Math.round(xScale * connection.getStationB().getxPos());
yPoints[0]=
(int)Math.round(yScale * connection.getStationA().getyPos());
yPoints[1]=
(int)Math.round(yScale * connection.getStationB().getyPos());
g.setColor(Color.GRAY);
g.drawPolyline(xPoints, yPoints,2);
int markX = xPoints[0]/2+ xPoints[1]/2;
int markY = yPoints[0]/2+ yPoints[1]/2;
g.setColor(Color.RED);
g.drawString(Double.toString(connection.getDistanc
e()),
markX, markY);
5. }
}
g.setColor(oldColor);
}
}
__MACOSX/student start_code_U08223_cwk1
(1)/._GraphicsUtil.java
student start_code_U08223_cwk1 (1)/Network.javastudent
start_code_U08223_cwk1 (1)/Network.javapackage cwk1test;
import java.util.Collection;
/**
*
* Interface to be implemented by classes that implement networ
ks
*
* N.B. You may change the package name for this interface, bu
t you should not
* modify it in any other way.
*/
publicinterfaceNetwork{
/**
* Add a station to the network
*
* @param name name of the station
* @param xPos x position at which station should be display
ed in a 255x255
* graph area
*
* @param yPos y position at which station should be display
ed in a 255x255
6. * graph area
*
*/
void addStation(String name,int xPos,int yPos);
/**
* Get a reference to the station with a specified name
*
* @param name name of the station
* @return If the network contains a station with the specifie
d name then a
* reference to that station is returned. Otherwise the return v
alue is
* null.
*/
Station getStation(String name);
/**
* Return a Collection containing all the stations in the netwo
rk
*
* @return a Collection containing all the stations in the netw
ork
*/
Collection<Station> getStations();
/**
* Return a Collection containing all the connections in the n
etwork
*
* @return a Collection containing all the connections in the
network
*/
Collection<Connection> getConnections();
/**
7. * Return a Collection containing all the Connections in the n
etwork that
* start or end at a specified station
*
* @param station Station to/from which the Connection shou
ld run
*
* @return a Collection containing all the connections that st
art or end at
* the specified station
*/
Collection<Connection> getConnectionsFrom(Station station);
/**
* Add a connection between two stations
*
* @param stationA name of one of the stations connected
* @param stationB name of the other station connected
* @param distance distance value for the connection
*
* PRECONDITION:
* getStation(StationA) != null
* && getStation(StationB) != null
* && getStations.contains(getStation(StationA)) &&
* getStations.contains(getStation(StationB)
*/
void addConnection(String stationA,String stationB,double dist
ance);
/**
* Delete all of the Stations and Connections in the Network
*/
void clear();
}
8. __MACOSX/student start_code_U08223_cwk1
(1)/._Network.java
student start_code_U08223_cwk1 (1)/Station.javastudent
start_code_U08223_cwk1 (1)/Station.java/**
* Interface to be implemented by classes that represent Stations
*
* N.B. You may change the package name for this interface, bu
t you should not
* modify it in any other way.
*/
package cwk1test;
import java.util.Collection;
publicinterfaceStation{
/**
* Get the name of the station
*
* @return the name of the station
*/
String getName();
/**
* Get the x position that the station would have when displa
yed in a
* 255x255 graph area
*
* @return the x position as specified above
*/
int getxPos();
/**
* Get the x position that the station would have when displa
9. yed in a
* 255x255 graph area
*
* @return the y position as specified above
*/
int getyPos();
}
__MACOSX/student start_code_U08223_cwk1
(1)/._Station.java
student start_code_U08223_cwk1 (1)/StationQueue.javastudent
start_code_U08223_cwk1 (1)/StationQueue.java/*
* To change this license header, choose License Headers in Pro
ject Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package cwk1test;
/**
* Interface to be implemented by queues of Stations
*
* N.B. You may change the package name for this interface, bu
t you should
* not modify it in any other way.
*/
publicinterfaceStationQueue{
/**
* Add a Station to the back of the queue
*
* @param s Station to be added
*/
void add(Station s);
10. /**
* Get the number of Stations in the queue
*
* @return number of stations in the queue
*/
int getSize();
/**
* Return, but do not remove, the station
* at the front of the queue
*
* @return the Station at the front of the queue
*
* PRECONDITION: queue is not empty
*/
Station peek();
/**
* Return, and remove, the station at the
* front of the queue
*
* @return the Station at the front of the queue
*
* PRECONDITION: queue is not empty
*/
Station remove();
}
__MACOSX/student start_code_U08223_cwk1
(1)/._StationQueue.java
student start_code_U08223_cwk1 (1)/StationStack.javastudent
start_code_U08223_cwk1 (1)/StationStack.java/*
* To change this license header, choose License Headers in Pro
11. ject Properties.
* To change this template file, choose Tools | Templates
* and open the template in the editor.
*/
package cwk1test;
/**
* Interface to be implemented by classes that represent stacks o
f Stations
*
* N.B. You may change the package name for this interface, bu
t you should not
* modify it in any other way.
*/
publicinterfaceStationStack{
/**
* Add a Station to the top of the stack
*
* @param s Station to be added
*/
void push(Station s);
/**
* Get the number of Stations in the queue
*
* @return number of stations in the queue
*/
int getSize();
/**
* Return, but do not remove, the station at the top of the stac
k
*
* @return the Station at the top of the stack
*
12. * PRECONDITION: stack is not empty
*/
Station peek();
/**
* Return, and remove, the station at the top of the stack
*
* @return the Station at the top of the stack
*
* PRECONDITION: stack is not empty
*/
Station pop();
}
__MACOSX/student start_code_U08223_cwk1
(1)/._StationStack.java
__MACOSX/._student start_code_U08223_cwk1 (1)
Coursework 1 (15 marks)
Introduction
This coursework requires you to write software to process
networks of train or
bus stations, which will be stored as text files, and can be
displayed in a
manner similar to that illustrated in Figure 1.
Figure 1 An Example Network
The text strings in the diagram represent stations, the lines
indicate the connections
13. between them, and the numbers indicate the distance you would
travel if you
traversed those connections (you can assume that these are
measured in kilometres,
but the units make no difference to the coursework).
For example there is a direct route from Kingsand to Rame that
is 20 kilometres long.
The connections are undirected so, for example if there is a
connection from
Kingsand to Rame, then there is also a connection from Rame to
Kingsand.
Networks such as that shown in Figure 1 are examples of data
structures known as
graphs. We will describe graphs more formally in weeks 4 and
5, but hopefully the
figure makes the general idea clear.
For this coursework, you are required to create a GUI
application that reads text files
that describe networks such as that shown in Figure 1, and
which analyses them in
various ways. The syntax of the text files is set out in Appendix
A. Here are the
functional and non-functional requirements that your
application must meet.
Functional Requirements
FR1 The GUI should contain the following elements:
1. An area in which a graphic view of the network can be
14. displayed. We
will call this the “graph area”.
2. A separate area in which a list of stations can be displayed.
We will call
this the “list area”.
3. Buttons marked “Read”, “Breadth”, and “Depth”.
FR2 When the “Read” button is clicked, the user should be
presented with a
dialog that allows him/her to pick a file. If this file contains
text that meets
the syntax set out in Appendix A, then the network that it
represents should
be displayed in the graph area. The network should be displayed
in such a
way as to respect the positions of stations, and the connections
between
them, that are described in the text file.
If the text file does not follow the syntax set out in Appendix A,
then an
error message should be displayed. This message does not need
to contain
any details about the syntax error; it simply needs to state that
there was an
error.
Hint: The files that you have been given include a file
GraphicsUtil.java that contains a graphical method that you will
find useful.
You can use this file without modification, or with
modification, or not use
it at all, as you desire.
FR3 When the user clicks on the “Breadth” button, the “list”
area should be
updated so that it displays a list of all the stations in the
network, in breadth
15. first order (see Appendix B). The start station for this traversal
should be
the first station defined in the text file from which the network
was read.
FR4 When the user clicks on the “Depth” button, the list area
should be updated
so that it displays a list of all the stations in the network, in
depth first order
(see Appendix B). The start station for this Traversal should be
the first
station defined in the text file from which the network was read.
Non-functional Requirements
NFR1 The program should contain classes that implement the
Connection,
Network, Station, StationQueue, and StationStack interfaces
that you will
find on the module website.
You may use inner classes where this is appropriate. For
example the class
that implements the Station interface could be an inner class of
the one that
implements the Network interface.
Hint: You may find that it helps if the class implementing
Network has a
private field with this declaration
private Map<String,Station> stationMap;
NFR2 The breadth first, and depth first, traversals referred to in
16. FR3 and FR4
should be carried out using the iterative algorithms set out in
Appendix B,
and the queue and stack referred to in that appendix should be
implemented
using classes that implement the StationStack and StationQueue
interfaces
NFR3 The program should be constructed without the use
NFR3 When the user clicks on the “Breadth” button, the “list”
area should be
updated so that it displays a list of all the stations in the
network, in breadth
first order (see Appendix B). The start station for this traversal
should be
the first station defined in the text file from which the network
was read.
What you have to submit:
You should submit two files:
1) A .zip file containing all of your code, preferably as a
Netbeans project.
2) A .doc, or .docx file containing a short reflection on the
degree to which you have
met the functional and non-functional requirements set out
above.
Mark Scheme
17. Appendix A: Format of the text files used.
The networks that are to be processed will be represented by
text files having the
following format (illustrated in Table 1):
Each station is represented by text in the form
Station: StationName XDisplay YDisplay
where StationName is the name of the station, which may
contain alphabetic
characters and underscores, but no other characters, and
XDisplay and YDisplay are
decimal integers in the range 0-255 which are used to indicate
where the station
should appear when the network is displayed on screen.
XDisplay and YDisplay are used to indicate where the stations
would appear if the
graph area was of size 255x255 pixels. You do not have to set
the graph area to
actually be 255x255 pixels, so long as you scale the displayed
graph in an appropriate
way. For example, if the text file assigned co-ordinates 100,100
to a particular station,
then that station could be displayed at position 100,100 on a
255x255 graph area, or
200,200 on a 512x512 graph area, and so on. Also the XDisplay
and YDisplay co-
ordinates should not be taken as representing the real world
geographical positions of
stations. Stations that are displayed in a way that makes them
look far apart may
actually be quite close in the real world (for example Kingsand
and Cawsand are quite
far apart in Figure 1, but the numbers on the graph indicate that
18. you can get from one
to the other by travelling only 5 kilometres).
N.B. You can make use of the GraphicsUtil class provided in
order to display the
network.
You should not assume that the text representing a station will
be all on one line.
You should not assume that all stations will be defined before
all connections.
However you can assume that, if a connection refers to a
station, then that station will
be defined before it is referred to.
Connections between stations are represented by lines of the
form
Connection: StationName1 StationName2 Distance
Where StationName1 and StationName2 are the names of the
two stations connected
(as specified by the bits of text beginning with “Station:”) and
Distance is the distance
value for the connection expressed as an number which may or
may not include a
decimal point.
Hint #1: You can read the text files using a Scanner. The use of
a Scanner to
read input streams coming from files was explained in module
U08009.
19. Hint #2: Because you cannot assume that each connection is on
a separate line, you
should not use the nextLine() method of the Scanner class. Use
the next() and
nextDouble() methods instead.
The network shown in Figure 1 might be represented by the text
shown in Table 2.
The line breaks in the text are deliberate, and illustrate that you
should not assume
that the text representing a station or connection will be on one
single line. The fact
that the definition of the Treninnow station comes after some of
the connection
definitions is also deliberate. Note that the definition of the
Treninnow station comes
before any connections that refer to it.
Table 1 Text representation of network in Figure 1
Station: Rame 65 120
Station: Antony 20 100
Station: Cawsand 130 60
Station: Kingsand 160 140
Station: Millbrook 65 100
Station: Penlee 110 120
Station: Polbathic 20
120
Connection: Rame Penlee 10
Connection: Rame Millbrook 15
Connection: Millbrook Cawsand 23
20. Connection: Cawsand Kingsand 5
Connection: Kingsand Rame 20
Station: Treninnow 110
100
Connection: Millbrook Treninnow 30
Connection: Millbrook Antony 35.3
Connection: Antony
Polbathic 22
Connection: Polbathic Rame 20
Appendix B: Breadth First and Depth First Traversal
Breadth First Traversal
In a breadth first traversal of a graph we visit all of the nodes
that can be reached from
a given start point by traversing one connection, then all those
that can be reached by
traversing two connections, and so on. So a possible breadth
first traversal of the
graph in Figure 1, starting at Rame would be:
Rame Penlee Kingsand Polbathic Millbrook Cawsand Antony
Treninnow.
You should use the following iterative algorithm to create a list
of nodes in breadth-
first order, beginning with a specified start station.
Let Q be a queue of Stations
Create an initially empty list of Stations, which we will call L
Add the start station to the back of Q
While Q is not empty BEGIN
Remove the Station at the front of Q, call this Station S
21. Add S to the end of L
For each station S2 that is adjacent to S BEGIN
If S2 is not in the list L then add it to the back of queue Q
END (For)
END (While)
Return L
Clarification: in the algorithm two stations are “adjacent” if that
you can get from
one station to the other without passing through any other
station. So for example in
Figure 1 Antony is adjacent to Millbrook, but not to Rame.
Note: it is possible to write a recursive algorithm for breadth
first traversal, but you
should not do so. We want an iterative algorithm as set out
above.
Depth First Traversal
In a depth first traversal of a graph we visit all of the nodes that
can be reached from a
given start point in the following manner:
We begin at the start point, then visit a station S2 that is
adjacent the start point, then
we try to visit an unvisited a station S3 that is adjacent to S2,
and so on. If we arrive
on a node from which we can go nowhere (because there are no
adjacent nodes that
we have not already visited) then we “backtrack” to a node
which we have already
visited but which has adjacent nodes that we have not visited.
22. So a depth first traversal of the graph in Figure 1, starting at
Rame would be: Rame
Millbrook Antony Polbathic Treninnow Cawsand Kingsand
Penlee.
You should use the following iterative algorithm to create a list
of stations in depth
first order, beginning with a specified start station.
Let S be a stack of Stations
Create an initially empty list of Stations, which we will call L
Push the start station onto the stack S
While S is not empty BEGIN
Pop the Station at the top of the stack. Call this Station T.
If T is not already in list L then add it to the back of that list.
For each station T2 that is adjacent to T BEGIN
If T2 is not in the list L then push it on to the top of the stack S
END (For)
END (While)
Return L
Note: it is possible to write a recursive algorithm for depth first
traversal, but you
should not do so. We want an iterative algorithm, as set out
above.