Skip to content

Stack & Queue Visualizer

1/1

What are stacks and queues?

A stack and a queue are linear collections that only let you add and remove items at fixed ends. A stack is LIFO (last in, first out): push and pop both happen at the top, while a queue is FIFO (first in, first out): enqueue at the rear, dequeue at the front. Implemented well, every one of these operations takes O(1) time.

Stack vs queue at a glance

  • Removal order: a stack returns the newest item first (LIFO); a queue returns the oldest item first (FIFO).
  • Where changes happen: a stack inserts and removes at the same end, the top; a queue inserts at the rear and removes at the front.
  • Operations: stack — push, pop, peek; queue — enqueue, dequeue, peek (or front).
  • Array bookkeeping: a stack needs one index (top); a queue needs two (front and rear), which is why array queues need the circular trick to reuse space.
  • Everyday picture: a pile of plates versus a line at a ticket counter.
  • Typical algorithms: depth-first search, backtracking and expression parsing use stacks; breadth-first search, scheduling and buffering use queues.

Put 1, 2, 3 into both: popping the stack gives 3, 2, 1 (reversed), dequeuing the queue gives 1, 2, 3 (preserved). That one property usually decides which a problem needs — "most recent first" points to a stack, "in arrival order" to a queue.

The four structures in this visualizer

  • Stack: an array plus a top index. Pushing onto a full array is an overflow; popping an empty one is an underflow.
  • Linear queue: an array whose front and rear only move right. It is simple, but slots freed by dequeue are never reused — the wasted-space problem.
  • Circular queue: the same array with indices that wrap around using % capacity, so every slot is reused and both operations stay O(1).
  • Deque: a double-ended queue that inserts and removes at both ends in O(1). Use one end and it is a stack; use both and it is a queue.

Classic stack applications

Stacks shine whenever the most recent unfinished thing has to be finished first. The Applications tab animates the four problems that appear in nearly every data-structures course and coding interview:

  • Balanced parentheses: push each opening bracket and match every closing bracket against the top.
  • Infix to postfix: the shunting-yard algorithm parks operators on a stack until precedence lets them out.
  • Postfix evaluation: push numbers and let each operator pop its two operands.
  • Next greater element: a monotonic stack answers "first larger value to the right" for every element in O(n).

Outside the classroom the same idea runs your program's call stack (each function call pushes a frame), the undo history of an editor, the back button of a browser and iterative depth-first search.

Where queues show up

  • Breadth-first search and level-order tree traversal process nodes in the order they were discovered.
  • Operating systems keep ready queues of processes, and printers keep a print queue.
  • Devices — keyboards, sound cards, network cards — buffer data in ring buffers, which are circular queues.
  • Message queues such as Kafka, RabbitMQ or SQS decouple fast producers from slow consumers.
  • Deques power the sliding-window maximum trick and 0-1 BFS.

A priority queue is the odd one out: it removes the highest-priority item rather than the oldest, so it is not FIFO. It is normally built on a binary heap.

Stacks and queues in real code

  • Python: a list is a fine stack (append, pop, s[-1]). For a queue use collections.deque (append, popleft) — list.pop(0) is O(n) because every remaining element shifts.
  • Java: prefer ArrayDeque for both (push/pop and offer/poll). The legacy Stack class is synchronized and extends Vector.
  • C++: std::stack and std::queue are adapters over std::deque; pop() returns nothing, so read top() or front() first.
  • JavaScript: arrays work as stacks (push/pop), but shift() is O(n), so large queues should keep a head index or use a ring buffer.

Interviewers love combining the two: implement a queue with two stacks (amortized O(1) per operation), a stack with queues, or a "min stack" that reports its minimum in O(1) by keeping a second stack of running minimums.

Time and space complexity

CaseTimeSpaceWhy
Stack push / pop / peekO(1)O(n)Only the top is touched; with a growable array, push is amortized O(1).
Queue enqueue / dequeueO(1)O(n)Circular array or linked list: two indices move, nothing shifts.
Deque at either endO(1)O(n)Same circular array, with front allowed to step backwards.
Search for a valueO(n)O(1)Neither structure is built for lookup — you scan.
list.pop(0) / array.shift()O(n)O(1)Removing the first element of an array shifts all the others.

Stack & Queue in Python

from collections import deque

stack = []                 # LIFO: use the end of a list
stack.append(1)            # push
stack.append(2)
stack.append(3)
print(stack.pop())         # 3 - the last one in comes out first
print(stack[-1])           # 2 - peek at the top

queue = deque()            # FIFO: O(1) at both ends
queue.append(1)            # enqueue at the rear
queue.append(2)
queue.append(3)
print(queue.popleft())     # 1 - the first one in comes out first
print(queue[0])            # 2 - peek at the front

The visualizer above shows the same code in Python, C++, Java and JavaScript.

Frequently asked questions

What is the difference between a stack and a queue?

A stack removes the most recently added item first (LIFO), while a queue removes the oldest item first (FIFO). A stack adds and removes at the same end; a queue adds at the rear and removes at the front.

Is a stack LIFO or FIFO?

A stack is LIFO — last in, first out. A queue is FIFO — first in, first out.

Which data structure does BFS use, and which does DFS use?

Breadth-first search uses a queue, so it explores nodes in order of distance from the start. Depth-first search uses a stack, either explicitly or through the recursion call stack.

How do you implement a queue using two stacks?

Push new items onto an *in* stack. To dequeue, pop from an *out* stack; when it is empty, first move everything from *in* to *out*, which reverses the order. Each item moves at most once, so every operation is amortized O(1).

Why use collections.deque instead of a list for a queue in Python?

deque.popleft() is O(1), while list.pop(0) is O(n) because every remaining element shifts left. For a stack, a plain list with append and pop is fine.

Are push and pop always O(1)?

In a linked-list stack, yes. In a dynamic array, push is amortized O(1): an occasional resize copies all n items, but averaged over many pushes the cost per push is constant.

Keep learning

Last updated