← drvivekkumar.info
Arrays & Memory Representation
How data is stored · Arrays vs Linked Lists · Pointers
Dr. Vivek KumarBennett University
Data Structure Internals

How Computers Store Data in Memory

Before studying stacks, queues, trees, or graphs, you need to understand one fundamental question: where exactly does data live in memory, and how do we find it again? The answer determines everything — how fast we can access it, insert into it, or delete from it. Two fundamental strategies exist: arrays and linked lists.

The Foundation
Memory as a Street of Houses

Think of computer memory as a very long street of numbered houses. Each house has an address (a number) and can hold exactly one value. When your program stores data, the operating system assigns it houses on this street. The question is: do you get houses that are next to each other, or houses scattered anywhere on the street?

This single choice — contiguous vs scattered — is what separates an array from a linked list. Every other difference in performance follows directly from it.

Raw memory — a sequence of addressed slots
—0x04
—0x08
—0x0C
—0x10
—0x14
—0x18
—0x1C
—0x20
Each slot holds one value. The address is fixed — it never changes. The value stored there can change at any time.
Key concept: An address is just a number. When your code says arr[3], the computer computes the address of slot 3 by arithmetic — it does not search for it. This is why array access is O(1).
Strategy 1
Arrays — Contiguous Memory

An array stores all its elements in consecutive memory addresses. If the array starts at address 0x04 and each integer takes 4 bytes, then element 0 is at 0x04, element 1 at 0x08, element 2 at 0x0C, and so on. The address of any element can be computed instantly with a simple formula.

Array: arr = [12, 35, 61, 48, 27] stored contiguously
120x04 [0]
350x08 [1]
610x0C [2]
480x10 [3]
270x14 [4]
—0x18
—0x1C
All five elements sit side by side. The OS reserved these 5 slots at the time the array was declared. The slots after 0x14 belong to other data.
Address formula — how arr[i] is found instantly
address(arr[i]) = base_address + i × element_size address(arr[3]) = 0x04 + 3 × 4 = 0x10 ✓

Because of this formula, random access is O(1) — you can jump directly to any element by index without scanning through others. This is the array's greatest strength.

✅
Strengths of Arrays
O(1) random access — jump to any index instantly using the address formula.

Cache friendly — elements are adjacent in memory, so the CPU loads several at once into its fast cache.

Simple iteration — just increment the index from 0 to n-1.
❌
Weaknesses of Arrays
Fixed size — declared at compile time (in C). You cannot grow or shrink without creating a new array.

O(n) insertion/deletion — inserting at position i requires shifting all elements from i onward.

Wasted space — if you declare size 100 but use 30, 70 slots are wasted.
Inserting 99 at index 1 — all elements from index 1 onward must shift right
12[0]
99[1] NEW
35→[2]
61→[3]
48→[4]
27→[5]
4 elements had to shift one position right to make room. For n elements, worst case is O(n) shifts — at the beginning of a large array this is expensive.
Strategy 2
Linked Lists — Scattered Memory with Pointers

A linked list stores elements anywhere in memory — elements do not need to be adjacent. Instead, each element (called a node) stores two things: its data value and the memory address of the next node. This address is called a pointer.

By following pointers from one node to the next, you can traverse the entire list — even though the nodes are physically scattered across memory.

Linked list: [12 → 35 → 61 → 48 → NULL] — nodes scattered in memory
12data
0x1Cnext
@0x04
→
35data
0x38next
@0x1C
→
61data
0x54next
@0x38
→
48data
NULLnext
@0x54
Notice the addresses: 0x04, 0x1C, 0x38, 0x54 — they are not consecutive. The nodes could be anywhere. Only the NEXT pointer connects them logically.
The pointer IS the connection. The value 0x1C stored in node 12's NEXT field is not just an arrow on a diagram — it is a real integer value sitting in memory. Changing that integer rewires the entire list. This is why linked list insert and delete are O(1) once you have the right position.
Inserting 99 between 12 and 35 — only 2 pointer changes needed
12data
0xA0next ✏️
→
99NEW
0x1Cnext ✏️
@0xA0
→
35data
0x38next
@0x1C
Only 2 changes: node 12's NEXT updated to point to new node, new node's NEXT set to 0x1C (old next). Node 35 and all others are untouched — O(1) work at the insertion point.
✅
Strengths of Linked Lists
Dynamic size — grows and shrinks at runtime by allocating or freeing individual nodes.

O(1) insert/delete — once you have the predecessor node, just update two pointers.

No wasted space — allocate exactly as many nodes as you need.
❌
Weaknesses of Linked Lists
O(n) access by index — to reach node i, you must follow pointers from HEAD through i nodes.

Extra memory — every node stores a pointer (8 bytes on 64-bit systems) in addition to the data.

Not cache friendly — nodes are scattered; each pointer-follow may cause a cache miss.
Types
Four Types of Linked Lists

The basic node structure can be extended in different ways, each adding new capabilities at the cost of a little extra memory per node.

1. Singly Linked List
12data
0x1Cnext
→
35data
0x38next
→
NULL

Each node has one pointer — to the next node. Traversal goes in one direction only. 2 fields per node. Used for stacks, simple queues, and hash table chaining.

2. Doubly Linked List
NULL
←
NULLprev
12data
0x1Cnext
⇌
0x04prev
35data
NULLnext

Each node has two pointers — to the next node AND to the previous node. Traversal works in both directions. 3 fields per node. Used for browser history, undo/redo, and deques.

3. Circular Linked List

Like a singly linked list, but the last node's NEXT points back to the first node instead of NULL. There is no end — traversal keeps going in a circle. Used for round-robin scheduling (CPU task management) and music playlist loops.

4. Sorted Linked List

Elements are always maintained in ascending order. Every insertion finds the correct position first (O(n) scan), then wires the new node in — keeping the list sorted at all times. Used as the basis for priority queues implemented with linked lists.

Side by Side
Array vs Linked List — When to Use Which
OperationArraySingly Linked ListDoubly Linked List
Access by indexO(1) ✓O(n) ✗O(n) ✗
Search (unsorted)O(n)O(n)O(n)
Insert at beginningO(n) — shift allO(1) ✓O(1) ✓
Insert at endO(1) — if spaceO(n) — find tailO(n) — find tail*
Insert at position iO(n) — shiftO(n) — traverseO(n) — traverse
Delete by valueO(n) — shiftO(n) — find pred.O(n) find, O(1) delete ✓
Memory per element1 word (data only)2 words (data + next)3 words (prev + data + next)
Dynamic resize❌ Fixed at declaration✓ Any time✓ Any time
Reverse traversalO(1) — decrement index❌ Not possibleO(1) — follow prev ✓

* O(1) if a TAIL pointer is maintained separately

Rule of thumb:
Use an array when you access elements by index frequently, the size is known in advance, and cache performance matters (e.g. matrix operations, sorting).
Use a linked list when you insert and delete frequently, size changes at runtime, and you rarely need random access (e.g. implementing stacks, queues, adjacency lists for graphs).
A Powerful Combination
Why Heaps Use Arrays Instead of Linked Lists

A heap is a tree — but it is always stored as an array, not as a linked list. This seems counterintuitive at first. The reason is the parent-child address formula: in a heap stored as an array, the children of node at index i are always at indices 2i+1 and 2i+2, and the parent of node at index i is at index ⌊(i-1)/2⌋.

This formula lets you jump directly to any parent or child in O(1) — no pointer chasing, no traversal. Storing the same heap as a linked list would lose this formula entirely, forcing O(n) searches for parent nodes.

Heap index formulas — all O(1)
Parent of node i = ⌊(i - 1) / 2⌋ Left child of i = 2i + 1 Right child of i = 2i + 2
This is why structure matters: The choice of array vs linked list is not just about speed — it determines which algorithms are even possible. The heap's O(log n) insert and delete only work because the parent formula works, which only works because the array is contiguous. A linked-list heap would lose its main advantage.
Interactive Learning
Explore With These Games

Heap Array vs Linked List shows you the exact moment the array formula O(1) vs linked list O(log n) matters for a heap structure. Node Forge lets you build linked list nodes from scratch — dragging DATA and NEXT fields together and wiring them into a live list.