mirror of
https://github.com/davidalves04/Trabalho-Pratico-SD.git
synced 2025-12-08 12:33:31 +00:00
Create TrafficLightThread Class
This commit is contained in:
@@ -261,7 +261,7 @@ public class IntersectionProcess {
|
||||
*
|
||||
* @param vehicle The vehicle that has crossed this intersection.
|
||||
*/
|
||||
private void sendVehicleToNextDestination(Vehicle vehicle) {
|
||||
public void sendVehicleToNextDestination(Vehicle vehicle) {
|
||||
String nextDestination = vehicle.getCurrentDestination();
|
||||
|
||||
try {
|
||||
@@ -460,6 +460,14 @@ public class IntersectionProcess {
|
||||
System.out.println("=".repeat(60));
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the Intersection (model) object managed by this process.
|
||||
* @return The Intersection object.
|
||||
*/
|
||||
public Intersection getIntersection() {
|
||||
return this.intersection;
|
||||
}
|
||||
|
||||
// --- Inner class for Vehicle Transfer Messages ---
|
||||
|
||||
/**
|
||||
|
||||
165
main/src/main/java/sd/engine/TrafficLightThread.java
Normal file
165
main/src/main/java/sd/engine/TrafficLightThread.java
Normal file
@@ -0,0 +1,165 @@
|
||||
package sd.engine;
|
||||
|
||||
import sd.IntersectionProcess;
|
||||
import sd.config.SimulationConfig;
|
||||
import sd.model.TrafficLight;
|
||||
import sd.model.TrafficLightState;
|
||||
import sd.model.Vehicle;
|
||||
|
||||
/**
|
||||
* Implements the control logic for a single TrafficLight
|
||||
* as a Runnable task that runs in its own Thread.
|
||||
*
|
||||
* This class fulfills the assignment requirements:
|
||||
* 1. Implements Runnable (to be executed by a Thread/ExecutorService).
|
||||
* 2. Implements the GREEN/RED cycle logic.
|
||||
* 3. Includes a graceful shutdown mechanism (via the 'running' flag).
|
||||
*/
|
||||
public class TrafficLightThread implements Runnable {
|
||||
|
||||
/**
|
||||
* The TrafficLight object (the *model*) that this thread controls.
|
||||
* Contains the queue and the state.
|
||||
*/
|
||||
private final TrafficLight light;
|
||||
|
||||
/**
|
||||
* The IntersectionProcess (the Process) that "owns" this thread.
|
||||
* Used to call methods on the process, such as sendVehicleToNextDestination().
|
||||
*/
|
||||
private final IntersectionProcess process;
|
||||
|
||||
/**
|
||||
* The simulation configuration, used to get timings (e.g., crossing time).
|
||||
*/
|
||||
private final SimulationConfig config;
|
||||
|
||||
/**
|
||||
* Volatile flag to control the graceful shutdown mechanism.
|
||||
* When set to 'false', the 'run()' loop terminates.
|
||||
*/
|
||||
private volatile boolean running;
|
||||
|
||||
/**
|
||||
* Constructor for the Traffic Light Thread.
|
||||
*
|
||||
* @param light The TrafficLight object (model) to be controlled.
|
||||
* @param process The parent IntersectionProcess (for callbacks).
|
||||
* @param config The simulation configuration (to get timings).
|
||||
*/
|
||||
public TrafficLightThread(TrafficLight light, IntersectionProcess process, SimulationConfig config) {
|
||||
this.light = light;
|
||||
this.process = process;
|
||||
this.config = config;
|
||||
this.running = false; // Starts as 'stopped'
|
||||
}
|
||||
|
||||
/**
|
||||
* The main entry point for the thread.
|
||||
* Implements the GREEN/RED cycle logic extracted from IntersectionProcess.
|
||||
*
|
||||
*/
|
||||
@Override
|
||||
public void run() {
|
||||
this.running = true;
|
||||
System.out.println("[" + light.getId() + "] Traffic light thread started.");
|
||||
|
||||
try {
|
||||
// Main thread loop, continues while 'running' is true
|
||||
// This 'running' flag is controlled by the parent IntersectionProcess
|
||||
while (running) {
|
||||
|
||||
// --- GREEN Phase ---
|
||||
light.changeState(TrafficLightState.GREEN); //
|
||||
System.out.println("[" + light.getId() + "] State: GREEN");
|
||||
|
||||
// Process vehicles in the queue
|
||||
processGreenLightQueue();
|
||||
|
||||
// Wait for green duration
|
||||
Thread.sleep((long) (light.getGreenTime() * 1000)); //
|
||||
|
||||
if (!running) break; // Check flag after sleep
|
||||
|
||||
// --- RED Phase ---
|
||||
light.changeState(TrafficLightState.RED); //
|
||||
System.out.println("[" + light.getId() + "] State: RED");
|
||||
|
||||
// Wait for red duration
|
||||
Thread.sleep((long) (light.getRedTime() * 1000)); //
|
||||
|
||||
}
|
||||
} catch (InterruptedException e) {
|
||||
// Apanha a InterruptedException (outra forma de parar a thread)
|
||||
System.out.println("[" + light.getId() + "] Traffic light thread interrupted.");
|
||||
this.running = false; // Garante que o loop termina
|
||||
}
|
||||
|
||||
System.out.println("[" + light.getId() + "] Traffic light thread stopped.");
|
||||
}
|
||||
|
||||
/**
|
||||
* Processes vehicles in the queue while the traffic light is GREEN.
|
||||
* Logic extracted from IntersectionProcess.processGreenLight()
|
||||
*
|
||||
*/
|
||||
private void processGreenLightQueue() throws InterruptedException {
|
||||
//
|
||||
while (running && light.getState() == TrafficLightState.GREEN && light.getQueueSize() > 0) {
|
||||
|
||||
Vehicle vehicle = light.removeVehicle(); //
|
||||
|
||||
if (vehicle != null) {
|
||||
// 1. Get the crossing time (t_sem)
|
||||
double crossingTime = getCrossingTimeForVehicle(vehicle); //
|
||||
|
||||
// 2. Simulate the time the vehicle takes to cross
|
||||
Thread.sleep((long) (crossingTime * 1000)); //
|
||||
|
||||
// 3. Update vehicle statistics
|
||||
vehicle.addCrossingTime(crossingTime); //
|
||||
|
||||
// 4. Update intersection statistics
|
||||
// (This requires getIntersection() to be public in IntersectionProcess)
|
||||
process.getIntersection().incrementVehiclesSent(); //
|
||||
|
||||
// 5. Call the parent Process to send the vehicle
|
||||
// (This requires sendVehicleToNextDestination() to be public in IntersectionProcess)
|
||||
process.sendVehicleToNextDestination(vehicle); //
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the crossing time for a vehicle based on its type.
|
||||
* Logic extracted from IntersectionProcess.getCrossingTimeForVehicle()
|
||||
*
|
||||
*
|
||||
* @param vehicle The vehicle.
|
||||
* @return The crossing time in seconds.
|
||||
*/
|
||||
private double getCrossingTimeForVehicle(Vehicle vehicle) {
|
||||
switch (vehicle.getType()) { //
|
||||
case BIKE:
|
||||
return config.getBikeVehicleCrossingTime(); //
|
||||
case LIGHT:
|
||||
return config.getLightVehicleCrossingTime(); //
|
||||
case HEAVY:
|
||||
return config.getHeavyVehicleCrossingTime(); //
|
||||
default:
|
||||
return config.getLightVehicleCrossingTime(); //
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Requests the thread to stop gracefully (graceful shutdown).
|
||||
* Sets the 'running' flag to false. The thread will finish
|
||||
* its current sleep cycle and exit the 'run()' loop.
|
||||
*/
|
||||
public void shutdown() {
|
||||
this.running = false;
|
||||
// (Note: If the thread is sleeping, it will only stop
|
||||
// *after* waking up. A more immediate shutdown would require
|
||||
// calling .interrupt() on the thread running this Runnable)
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user