How about this?
Code:
package simulation;
import java.io.IOException;
//Tunnel class
class Tunnel {
public int allowed;
public Tunnel(int first) {
allowed = first;
}
public void useTunnel(Train t) {
/*
* the tunnel is a shared resource between Train 1 and 2 .so we should use a
* synchronized block to lock the object "Tunnel" from being accessed
* simultaneousely by Train 1 and 2
*
* if t is not allowed, wait
*/
if (t.getId() != allowed) {
System.out.println("Train " + t.getId() + " not allowed to enter tunnel. Waiting.");
synchronized (this) {
try {
this.wait();
} catch (InterruptedException ie) {
ie.printStackTrace();
}
}
}
//original code: synchronized (this) {
System.out.println("Train " + t.getId() + " enters tunnel");
t.travel(20); // train takes 20 time unit to go through tunnel
System.out.println("Train " + t.getId() + " exits tunnel");
//}
// Change allowed and wake up waiter
synchronized (this) {
allowed = (allowed == 1) ? 2 : 1;
System.out.println("Train " + allowed + " is ok to enter tunnel.");
this.notify();
}
}
}
//Train class
class Train extends Thread {
private static Tunnel tun = new Tunnel(1); // only one tunnel
// Simulate class
private int id; // id identifies each train
public Train(int id) {
// each train has a different identifing number
this.id = id;
}
public void run() {
// each train makes 2 loops
for (int j = 0; j < 3; j++) {
System.out.println("Train " + id + " leaves station");
travel(10); // train takes 10 time units to travel from station to tunnel
System.out.println("Train " + id + " arrives at tunnel");
tun.useTunnel(this); // current train uses tunnel
travel(15); // train takes 15 time units to travel from tunnel to station
System.out.println("Train " + id + " arrives at station");
travel(5); // train stays in station for 5 time units
}
}
public int getId() {
return id;
}
public void travel(int time) {
int limit = 500000 * id;
for (int j = 0; j < time; j++) {
for (int k = 0; k < limit; k++) {
double r = j / 2 * 2;
}
}
}
}
public class Simulate {
public static void main(String[] args) {
// ***************************************
Train t1 = new Train(1);
t1.start();
Train t2 = new Train(2);
t2.start();
// Wait for both Trains to finish.
try {
t1.join();
t2.join();
} catch (InterruptedException ie ) {
ie.printStackTrace();
}
// Keeps output on screen until Return is pressed
System.out.println("Type return to terminate program");
try {
System.in.read();
} catch (IOException e) {
}
}
}
Bookmarks