1. Problem Requirements & Functional Scope
An elevator system controls multiple elevator cars in a building with $N$ floors. The system must process external hall calls (floor up/down buttons) and internal car requests (destination floor buttons).
Key goals: Minimize average wait time, prevent starvation, handle emergency stops, enforce weight limits, and maintain thread safety under concurrent requests from multiple floors.
- Elevator States: MOVING_UP, MOVING_DOWN, IDLE, MAINTENANCE
- Door States: OPEN, OPENING, CLOSING, CLOSED
- Sensors: WeightSensor, ObstacleSensor
- Dispatching: LOOK algorithm (sweep in current direction until no more requests)
2. Class Diagram & Object-Oriented Modeling
Core classes include `ElevatorCar`, `ElevatorController`, `Dispatcher`, `HallButton`, `CarButton`, and the `ElevatorState` interface.
Using the State Pattern decouples motion state transitions from the elevator car logic. When moving UP, pressing a floor below the car is queued for the return journey rather than causing erratic directional shifts.
3. The LOOK Dispatching Algorithm
The LOOK algorithm mimics a disk drive head: an elevator continues traveling in its current direction servicing requests until there are no further requests ahead. Only then does it reverse direction.
Requests are stored in two priority queues: `upQueue` (min-heap for floors above) and `downQueue` (max-heap for floors below).
4. Complete Implementation & Code Walkthrough
Below is the core object-oriented implementation showing the State pattern and thread-safe request dispatching:
enum Direction { UP, DOWN, IDLE }
enum DoorState { OPEN, CLOSED }
interface Request {
floor: number;
direction: Direction;
}
class ElevatorCar {
public id: number;
public currentFloor: number = 0;
public direction: Direction = Direction.IDLE;
public doorState: DoorState = DoorState.CLOSED;
public upRequests = new Set<number>();
public downRequests = new Set<number>();
constructor(id: number) { this.id = id; }
public addRequest(floor: number) {
if (floor > this.currentFloor) {
this.upRequests.add(floor);
} else if (floor < this.currentFloor) {
this.downRequests.add(floor);
}
}
public step() {
if (this.direction === Direction.UP) {
if (this.upRequests.size > 0) {
this.currentFloor++;
if (this.upRequests.has(this.currentFloor)) {
this.upRequests.delete(this.currentFloor);
this.openDoor();
}
} else if (this.downRequests.size > 0) {
this.direction = Direction.DOWN;
} else {
this.direction = Direction.IDLE;
}
}
}
private openDoor() { this.doorState = DoorState.OPEN; }
}Model this architecture on the HLDForge Canvas
Turn static box diagrams into living, collaborative systems. Drag and drop microservices, Kafka clusters, and cache tiers. Run automated SPOF detection and STRIDE threat modeling in real time.
Written by HLDForge Architecture Team
Lead Machine Coding Specialist
The HLDForge Architecture Team publishes practical engineering guides, real-world case studies, and high-concurrency blueprints to help engineers build scalable and fault-tolerant software.