Kelick Tech Hub

Build, learn & keep up — tech, Linux & sports news included.

C++ Railway Reservation System Project

Intermediate•2–3 days•queues, classes, file handling

Book train seats, manage waitlists, and cancel with automatic promotion.

Share on X

What you will build

Trains with fixed seats, passengers booking and cancelling, and a waitlist that promotes the next person the moment a seat frees up. The waitlist logic — a queue with fair promotion — is the beating heart of every booking system on earth.

What you will learn

Feature checklist

Starter code

#include <iostream>
#include <queue>
#include <string>

struct Booking { std::string pnr, passenger; bool confirmed; };

class Train {
    std::string name_, route_;
    int seatsLeft_;
    std::queue<Booking> waitlist_;
public:
    Train(std::string n, std::string r, int seats)
        : name_(std::move(n)), route_(std::move(r)), seatsLeft_(seats) {}

    Booking book(const std::string& passenger, const std::string& pnr) {
        if (seatsLeft_ > 0) {
            --seatsLeft_;
            return {pnr, passenger, true};
        }
        Booking b{pnr, passenger, false};
        waitlist_.push(b);
        return b;
    }

    // Returns the promoted passenger's name, or "" if nobody waited.
    std::string cancel() {
        ++seatsLeft_;
        if (waitlist_.empty()) return "";
        Booking next = waitlist_.front(); waitlist_.pop();
        --seatsLeft_;
        return next.passenger;   // this passenger is now confirmed
    }
    int seatsLeft() const { return seatsLeft_; }
    size_t waiting() const { return waitlist_.size(); }
};

Full walkthrough

Step 1: Model Train and Booking separately

struct Train { id, name, from, to, time, capacity } is the static offer; struct Booking { ref, trainId, passenger, status } is one person's claim on it, where status is CONFIRMED or WAITLISTED. class TrainSystem (or the starter's design) owns vectors of both. The reference code — a short unique string like 'BK7F3' — is generated per booking so passengers can look theirs up without an ID number.

Step 2: book(): capacity is counted, never stored

Count existing CONFIRMED bookings for the train: below capacity → the new booking is CONFIRMED; at capacity → it joins the waitlist (a std::queue of booking refs, or the bookings vector filtered by status and order). Deriving the count from the bookings list keeps one source of truth — the recurring theme of this whole level of the catalogue.

Status book(...) {
    if (confirmedCount(trainId) < train.capacity)
        return Status::Confirmed;
    return Status::Waitlisted;  // FIFO order preserved
}

Step 3: cancel(): where the waitlist earns its keep

Find the booking by ref, mark it cancelled and remove it. If it was CONFIRMED, a seat just freed: promote the FIRST waitlisted booking for that train to CONFIRMED and say who got promoted. FIFO order is a fairness promise — promote out of order and your system is technically correct and socially broken.

Step 4: Look up bookings by reference code

A linear search over bookings by ref prints the passenger, train, route, and live status. Note 'live': a waitlisted booking may have been promoted since it was made, so always report the CURRENT status from the record, never a status cached at booking time.

Step 5: Print the train chart

For one train: capacity, confirmed count, waitlist count, and the passenger list in order. This is the report conductors print — building it forces your derived counts and your promotion logic to agree in public, which is exactly the kind of consistency check you want before calling the project done.

Step 6: Add trains through an admin path

Admins add trains (route, departure time as text, seat capacity) which are saved alongside bookings. Times as strings are fine here — the system never subtracts them, it only displays them (the same type-choice reasoning as the temperature logger's dates).

Step 7: Test the promotion story end-to-end

Create a train with capacity 2. Book three passengers: first two CONFIRMED, third WAITLISTED #1. Cancel the first booking: the third passenger must be promoted automatically and the chart must read 2 confirmed, 0 waitlisted. That single story exercises book, cancel, promotion, and reporting together.

Common mistakes

Compile and run

g++ -std=c++17 -o railway railway.cpp

Sample run

$ ./railway
1) Book  2) Cancel  3) My booking  4) Train chart  0) Exit
> 1
Passenger name:
> Ada Lovelace
Booked! Ref BK7F3 — CONFIRMED (T100 Lagos -> Ibadan 07:30, 1 seat left)
> 1
Passenger name:
> Bola Ahmed
Booked! Ref BK7F4 — CONFIRMED (train now full)
> 1
Passenger name:
> Chidi Okafor
Train full — Ref BK7F5 — WAITLISTED #1
> 2
Booking ref to cancel:
> BK7F3
Cancelled BK7F3 (Ada Lovelace).
Seat freed — BK7F5 (Chidi Okafor) promoted from the waitlist to CONFIRMED.
> 4
T100 Lagos -> Ibadan 07:30 — confirmed 2 · waitlist 0
> 0

Try it in your browser

No browser demo is included for this project. Build the C++ version below — that is the real program.

Related Intermediate projects

← All 60 projects · Classic site (Learn & Sandbox)

Download Fake GPS