Lesson 35 of 50 intermediate

Queue — The Lunch Line

First In, First Out — fair and orderly, just like a real line!

Open interactive version (quiz + challenge)

Real-world analogy

A queue is like the line at an ice cream shop. The first person who arrives gets served first. New people join at the BACK of the line, and people leave from the FRONT. You can't cut in line! First In, First Out — that's FIFO, and it's the fairest system there is!

What is it?

A queue is a fundamental data structure that follows the FIFO (First In, First Out) principle. Elements are added at the back and removed from the front, just like a real-world line. Queues are essential for BFS, scheduling, and any problem where order matters. They're the fair counterpart to stacks!

Real-world relevance

Every line you've ever stood in — at the grocery store, amusement park, or cafeteria — is a queue. Your computer uses queues to manage print jobs, network packets, and process scheduling. Music playlists are queues (next song plays first). Even hospitals use priority queues to decide which patients get treated first!

Key points

Code example

#include <bits/stdc++.h>
using namespace std;

int main() {
    // Basic queue operations
    queue<int> q;
    q.push(10);   // Queue: [10]         (front -> back)
    q.push(20);   // Queue: [10, 20]
    q.push(30);   // Queue: [10, 20, 30]
    
    cout << "Front: " << q.front() << "\n";  // 10
    cout << "Back: " << q.back() << "\n";     // 30
    cout << "Size: " << q.size() << "\n";     // 3
    
    q.pop();  // Remove 10. Queue: [20, 30]
    cout << "Front after pop: " << q.front() << "\n";  // 20
    
    // Process a line of customers
    queue<string> customers;
    customers.push("Alice");
    customers.push("Bob");
    customers.push("Charlie");
    
    cout << "\nServing customers:\n";
    while (!customers.empty()) {
        cout << "Now serving: " << customers.front() << "\n";
        customers.pop();
    }
    // Output: Alice, Bob, Charlie (in order!)
    
    // Simulation: Hot Potato game
    // N kids in a circle, pass potato K times, person holding it is out
    int n = 5, k = 3;
    queue<int> circle;
    for (int i = 1; i <= n; i++) circle.push(i);
    
    cout << "\nHot Potato (n=5, k=3):\n";
    while (circle.size() > 1) {
        for (int i = 0; i < k - 1; i++) {
            circle.push(circle.front());  // Pass to the back
            circle.pop();
        }
        cout << "Player " << circle.front() << " is out!\n";
        circle.pop();  // Remove the one holding the potato
    }
    cout << "Winner: Player " << circle.front() << "\n";
    
    return 0;
}

Line-by-line walkthrough

  1. 1. #include — includes everything, including the queue library.
  2. 2. queue q; — creates an empty queue that holds integers.
  3. 3. q.push(10); q.push(20); q.push(30); — adds elements to the BACK of the queue. After these, 10 is at the front and 30 is at the back.
  4. 4. q.front() returns 10 (the first element added) and q.back() returns 30 (the last element added). Unlike stack, queue lets you see both ends!
  5. 5. q.pop(); — removes the FRONT element (10). Now 20 is at the front. This is the key difference from stack — stack pops from the top (back), queue pops from the front.
  6. 6. The customer serving loop: while the queue isn't empty, print the front customer's name and pop them. Since it's FIFO, Alice (first in) gets served first!
  7. 7. Hot Potato simulation: we put players 1-5 in a queue. To pass the potato, we move the front person to the back (push front, then pop). After k-1 passes, the person at front is 'out' — we pop them without re-adding.
  8. 8. circle.push(circle.front()); circle.pop(); — this moves the front person to the back of the queue, simulating passing the potato around a circle. Clever use of the queue!
  9. 9. The loop continues until only 1 player remains — they're the winner!

Spot the bug

#include <bits/stdc++.h>
using namespace std;

int main() {
    queue<int> q;
    q.push(1);
    q.push(2);
    q.push(3);
    
    for (int i = 0; i < 3; i++) {
        cout << q.back() << " ";
        q.pop();
    }
    return 0;
}
Need a hint?
Look at which end we're reading from vs which end pop() removes from. Are we getting the behavior we expect?
Show answer
The bug is using back() instead of front()! The code prints q.back() which is the LAST element, but q.pop() removes from the FRONT. So it prints 3, 3, 3 (back keeps changing as front elements are removed) instead of 1, 2, 3. The fix is to change q.back() to q.front(). Then we'll correctly see each element as it leaves the queue in FIFO order: 1, 2, 3.

Explain like I'm 5

Imagine you're at a water slide. People wait in a line. The first person who got in line goes down the slide first. New people join at the END of the line. Nobody cuts! That's a queue — the first person to join is the first person to go. It's fair, simple, and exactly how your computer handles many tasks!

Fun fact

The Hot Potato game we coded is actually a famous mathematical problem called the Josephus Problem, named after historian Josephus Flavius from ancient Rome! It has been studied by mathematicians for over 2000 years. There's even a formula to find the winner directly without simulation!

Hands-on challenge

Simulate a printer queue! Read n print jobs (each with a name and number of pages). Process them in FIFO order, printing 'Printing [name] ([pages] pages)' for each. At the end, print the total pages printed. Bonus: implement a 'priority' system where jobs with fewer pages get printed first (hint: use a priority queue)!

More resources

Open interactive version (quiz + challenge) ← Back to course: CP Zero to Hero