Arrays are brilliant when you know the size of your data upfront. But what happens when data arrives unpredictably - a stream of sensor readings, a queue of tasks for an AI to process, or a conversation history that grows with every message? You need structures that grow and shrink gracefully.
Enter linked lists, stacks, and queues - the dynamic trio.
A linked list stores items as a chain of nodes. Each node holds two things: the data itself, and a pointer (reference) to the next node in the chain.
[data: "A" | next: โ] โ [data: "B" | next: โ] โ [data: "C" | next: null]
Unlike arrays, linked list nodes don't sit side by side in memory. They can be scattered anywhere - the pointer simply tells you where to find the next one.
| Operation | Array | Linked List | |-----------|-------|-------------| | Access by index | O(1) โก | O(n) ๐ข | | Insert at beginning | O(n) ๐ข | O(1) โก | | Insert in middle | O(n) ๐ข | O(1)* โก | | Delete from middle | O(n) ๐ข | O(1)* โก | | Memory usage | Compact | Extra (pointers) |
*Once you've found the position - finding it is still O(n).
Your browser's tab bar lets you open, close, and rearrange tabs freely. Would an array or a linked list be a better fit for managing the list of open tabs? Consider what happens when you close a tab in the middle.
A stack works exactly like a stack of plates: you add to the top and remove from the top. The last item placed on the stack is the first one taken off.
Sign in to join the discussion
Push "A" โ [A]
Push "B" โ [A, B]
Push "C" โ [A, B, C]
Pop โ [A, B] (removed "C")
Pop โ [A] (removed "B")
Two operations define a stack:
Both are O(1) - instant, regardless of stack size.
When you see a "stack overflow" error, it literally means the call stack has run out of space - usually because a function keeps calling itself without stopping (infinite recursion). The famous developer Q&A site Stack Overflow is named after this very error.
You're implementing an 'undo' feature for a drawing application. Which data structure best models the history of actions?
A queue works like a queue at a shop: the first person to join is the first person served. Items are added at the back and removed from the front.
Enqueue "A" โ [A]
Enqueue "B" โ [A, B]
Enqueue "C" โ [A, B, C]
Dequeue โ [B, C] (removed "A")
Dequeue โ [C] (removed "B")
Two operations define a queue:
An AI API receives 10,000 requests per second. Which structure ensures requests are processed in the order they arrive?
There's also a priority queue, where items are dequeued based on priority rather than arrival order. AI systems use priority queues to process urgent tasks first - for example, a self-driving car might prioritise obstacle detection over route planning.
Language models process text as sequences. Under the hood, frameworks like PyTorch and TensorFlow use linked-list-like structures to build computation graphs - chains of operations where each step points to the next.
When training a neural network, memory is constantly allocated and freed as tensors (multi-dimensional arrays) are created and destroyed. Memory allocators often use linked lists of free memory blocks, finding suitable spaces for new tensors.
A chatbot needs to remember the last 10 messages in a conversation but discard older ones. Would you use a stack, a queue, or something else? What happens when the 11th message arrives?
Which statement about linked lists is FALSE?
The undo history in most applications has a limit - typically 100 to 1,000 actions. Without this limit, the stack would consume ever-growing memory. Some advanced systems use a combination of a stack and a queue (a "deque") to keep the most recent actions whilst discarding the oldest.