Bubble Sort is a simple comparison-based sorting algorithm. It repeatedly compares adjacent elements and swaps them if they are in the wrong order.
It is called "bubble" sort because after each pass, the largest unsorted element gradually moves toward the end of the array, as if it is bubbling upward.
Bubble Sort works by making repeated passes over the array:
After the first pass, the largest element is guaranteed to be in the last position. After the second pass, the second-largest element is fixed, and so on.
During one complete pass, whenever a larger element is on the left of a smaller element, they are swapped. Because of repeated adjacent swaps, the largest remaining element keeps moving right until it reaches the last unsorted position.
This is the key invariant of Bubble Sort: after each pass, the suffix at the end becomes sorted and does not need to be checked again.
The basic version always performs all passes, even if the array becomes sorted earlier. The optimized version uses a swapped flag and stops early if no swap happens during a pass.
This optimization is important because it changes the best-case running time from O(n^2) to O(n) for already sorted input.
Consider the array [5, 3, 8, 1, 2].
| Pass | What Happens | Array After Pass |
|---|---|---|
| Pass 1 | 5 swaps with 3, then 8 swaps past 1 and 2 | [3, 5, 1, 2, 8] |
| Pass 2 | 5 swaps with 1 and 2 | [3, 1, 2, 5, 8] |
| Pass 3 | 3 swaps with 1 and 2 | [1, 2, 3, 5, 8] |
| Pass 4 | No swap needed | [1, 2, 3, 5, 8] |
The array becomes sorted by repeatedly correcting local inversions between neighboring elements.
public class BubbleSortBasic {
static void bubbleSort(int[] arr) {
int n = arr.length;
for (int i = 0; i < n - 1; i++) {
for (int j = 0; j < n - i - 1; j++) {
if (arr[j] > arr[j + 1]) {
int temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
}
}
}
public class BubbleSortOptimized {
static void bubbleSort(int[] arr) {
int n = arr.length;
for (int i = 0; i < n - 1; i++) {
boolean swapped = false;
for (int j = 0; j < n - i - 1; j++) {
if (arr[j] > arr[j + 1]) {
int temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
swapped = true;
}
}
if (!swapped) {
break;
}
}
}
}
| Case | Time Complexity | Space Complexity | Explanation |
|---|---|---|---|
| Best case | O(n) | O(1) | Already sorted array with optimization |
| Average case | O(n^2) | O(1) | Typical unsorted input |
| Worst case | O(n^2) | O(1) | Reverse-sorted array |
Bubble Sort is an in-place algorithm because it uses only a constant amount of extra memory.
A sorting algorithm is stable if equal elements keep their original relative order after sorting.
Bubble Sort is stable because it swaps elements only when the left element is strictly greater than the right one. Equal elements are not forced to cross each other.
For the array [64, 34, 25, 12, 22, 11, 90]:
| Pass | Array State | Observation |
|---|---|---|
| Initial | [64, 34, 25, 12, 22, 11, 90] | Unsorted array |
| Pass 1 | [34, 25, 12, 22, 11, 64, 90] | 90 is already largest, 64 moves near the end |
| Pass 2 | [25, 12, 22, 11, 34, 64, 90] | 64 reaches its final position |
| Pass 3 | [12, 22, 11, 25, 34, 64, 90] | 34 becomes fixed |
| Pass 4 | [12, 11, 22, 25, 34, 64, 90] | 25 becomes fixed |
| Pass 5 | [11, 12, 22, 25, 34, 64, 90] | Array becomes sorted |
| Aspect | Bubble Sort | Selection Sort | Insertion Sort |
|---|---|---|---|
| Main idea | Swap adjacent out-of-order elements | Select minimum and place it correctly | Insert each element into the sorted portion |
| Best case | O(n) with optimization | O(n^2) | O(n) |
| Stable | Yes | No | Yes |
| Swaps / shifts | Can be many swaps | Usually fewer swaps | Usually many shifts |
| Best use case | Teaching and small nearly sorted input | When writes are expensive | Small or nearly sorted arrays |
Avoid Bubble Sort for large or performance-sensitive datasets.
Explore 500+ free tutorials across 20+ languages and frameworks.