1. Sorting Arrays (Bubble Sort)
Bubble Sort
A sorting algorithm is a procedure that arranges the elements in a collection (array)
so that they are ordered based on some property. For example:
* given an array of numbers we may want to arrange its elements in ascending order
* given an array of students we may want to arrange the students in descending order by GPA
One of the simplest sorting algorithms is Bubble Sort which works as follows:
1. Perform one complete run through the array swapping every pair of
elements that are out of order
2. Repeat step 1 until the array is sorted.
Out of order depends on how we want the array to be sorted. If we need an array
of increasing values, out of order means first is bigger than second. If we need
an array of decreasing values, out of order means first is smaller than second.
Here is a visualization of the process from Wikipedia:
Here is a visualization of Bubble Sort through a dance:
Here is another example of the execution of the algorithm:
original: 7 4 1 8 3 2 6 5
after run 1: 4 1 7 3 2 6 5 8
after run 2: 1 4 3 2 6 5 7 8
after run 3: 1 3 2 4 5 6 7 8
after run 4: 1 2 3 4 5 6 7 8
after run 5: 1 2 3 4 5 6 7 8 Done! No swaps made!
Bubble Sort Observations
We made a couple of observations about the way the algorithm works:
Observation 1
After 1-st run, the 1-st largest element ends up in the correct spot
2-nd run, the 2-nd largest ...
3-rd run, the 3-rd largest ...
... ...
k-th run, the k-th largest ...
... ...
(n-1)-th run the (n-1)-th largest element ends up in the correct spot
(at this point the n-th element must also be in its correct spot)
So after n-1 runs we are guaranteed that all elements
will end up in their correct locations.
Observation 2
Based on observation 2. we noticed that each run needs to examine fewer pairs
of elements. (Initially there are n-1 pairs --- for a total of n elements):
On the 1-st run we need to look at n-1 pairs (all pairs)
2-nd run n-2 pairs (all but 1 pair)
3-rd run n-3 pairs (all but 2 pairs)
... ...
k-th run n-k pairs
... ...
(n-1)-th run n-(n-1) = 1 pair
n-th run n-n = 0 pairs -- no need to do it!
Observation 3
The algorithm does not necessarily need to perform *n-1* runs to sort the array.
The number of runs depends on the arrangement of the elements --- in the extreme
case when the array is already sorted, only one run is needed to discover that no
swaps need to be made and stop the process.
In general, the algorithm stops when the latest run made no swaps at all.
Here is a summary of the above observations:
1. After the k-th run the k-th biggest element ends up in its correct position.
_______________ ________________________________________
|___scrambled___|___k are ordered and in correct spots___|
2. The k-th run only needs to traverse n-k pairs
(where *n* is the number of elements in the array).
3. The algorithm stops as soon as a particular run does no swaps.
Bubble Sort Implementation
Below is the code for an inefficient version of bubble sort. It does not take into
account any of the previous observations. Instead, it simply executes *n-1* runs through
the array. Since at each run one element gets put in its proper place, at the end all
elements will be in the correct location.
// does one run of the bubble sort algorithm -- every
// pair of neighbors that are out of order are swapped
void bubbleRun( int[] numbers )
{
for ( int i = 0 ; i < numbers.length-1 ; i = i + 1 )
{
if ( numbers[i] > numbers[i+1] ) // if out of order:
{
int temp = numbers[i];
numbers[i] = numbers[i+1];
numbers[i+1] = temp;
}
}
}
// sorts an array in increasing order -- simply executes *n-1*
// bubble runs through the array, where *n* is the array length
void bubbleSort( int[] numbers )
{
int n = numbers.length;
for ( int run = 1; run <= n-1; run = run + 1 )
{
bubbleRun( numbers );
}
}
Notice that nothing was returned in the methods above. The effect of the
methods is achieved through the modification of the given array, so the
return value (result) is implicit.