Insertion Sort
Build a sorted sequence by inserting each element into its correct position.
Insertion Sort
Insertion sort builds the sorted array one element at a time. At each step, it takes the next element and inserts it into the correct position within the already sorted prefix.
It mirrors the process of sorting cards in hand. Compared to swap-based methods, it reduces writes by shifting elements.
Problem
Given a sequence $A$ of length $n$, reorder it such that
$$ A[0] \le A[1] \le \cdots \le A[n-1] $$
Algorithm
Maintain a sorted prefix $A[0..i-1]$. Insert $A[i]$ into its correct position by shifting larger elements to the right.
insertion_sort(A):
n = length(A)
for i from 1 to n - 1:
key = A[i]
j = i - 1
while j >= 0 and A[j] > key:
A[j + 1] = A[j]
j = j - 1
A[j + 1] = key
Example
Let
$$ A = [5, 2, 4, 6, 1, 3] $$
Step 1:
Insert 2 into [5]
→ [2,5,4,6,1,3]
Step 2:
Insert 4 into [2,5]
→ [2,4,5,6,1,3]
Step 3:
Insert 6 into [2,4,5]
→ [2,4,5,6,1,3]
Step 4:
Insert 1 into [2,4,5,6]
→ [1,2,4,5,6,3]
Final result:
$$ [1,2,3,4,5,6] $$
Correctness
At iteration $i$, the prefix $A[0..i-1]$ is sorted. The algorithm inserts $A[i]$ into the correct position within this prefix by shifting all larger elements. This preserves sorted order and extends the sorted prefix by one element.
Complexity
| case | comparisons | time |
|---|---|---|
| best (already sorted) | $n$ | $O(n)$ |
| worst | $\frac{n(n-1)}{2}$ | $O(n^2)$ |
| average | $\approx \frac{n^2}{2}$ | $O(n^2)$ |
Space complexity:
$$ O(1) $$
Properties
- stable
- in-place
- adaptive to nearly sorted input
- efficient for small arrays
When to Use
Insertion sort performs well when the input is small or nearly sorted. It is commonly used as a base case inside more advanced algorithms such as quicksort or mergesort.
Implementation
def insertion_sort(a):
for i in range(1, len(a)):
key = a[i]
j = i - 1
while j >= 0 and a[j] > key:
a[j + 1] = a[j]
j -= 1
a[j + 1] = key
return a
func InsertionSort[T constraints.Ordered](a []T) {
for i := 1; i < len(a); i++ {
key := a[i]
j := i - 1
for j >= 0 && a[j] > key {
a[j+1] = a[j]
j--
}
a[j+1] = key
}
}