There are many different cases in which sorting an array can be useful. Algorithms (such as searching to see if a number exists in an array) can often be made simpler and/or more efficient when the input data is sorted. Furthermore, sorting is often useful for human readability, such as when printing a list of names in alphabetical order.
Sorting is generally performed by repeatedly comparing pairs of array elements, and swapping them if they meet some criteria. The order in which these elements are compared differs depending on which sorting algorithm is used, and the criteria depends on how the list will be sorted (ascending or descending order). To swap two elements, we can use the swap() function from the C++ standard library. Swap is defined in the algorithm header, and lives in the std namespace.
#include <algorithm> // for swap
#include <iostream>
int main()
{
using namespace std;
int x = 2;
int y = 4;
cout << "Before swap: x = " << x << ", y = " << y << endl;
swap(x, y); // swap also lives in std namespace
cout << "After swap: x = " << x << ", y = " << y << endl;
}
This program prints:
Before swap: x = 2, y = 4 After swap: x = 4, y = 2
Note that after the swap, the values of x and y have been interchanged!
Selection sort
There are many ways to sort an array. Selection sort is probably the easiest sort to understand, which makes it a good candidate for teaching even though it is one of the slower sorts.
Selection sort performs the following steps:
1) Starting at index 0, search the entire array to find the smallest value
2) Swap the smallest value found with the value at index 0
3) Repeat steps 1 & 2 starting from the next index
In other words, we’re going to find the smallest element in the array, and put it in the first position. Then we’re going to find the next smallest element, and put it in the second position. This process will be repeated until we run out of elements.
Here is an example of this algorithm working on 5 elements. Let’s start with a sample array:
{ 30, 50, 20, 10, 40 }
First, we find the smallest element, starting from index 0:
{ 30, 50, 20, 10, 40 }
We then swap this with the element at index 0:
{ 10, 50, 20, 30, 40 }
Now that the first element is sorted, we can ignore it. Consequently, we find the smallest element, starting from index 1:
{ 10, 50, 20, 30, 40 }
And swap it with the element in index 1:
{ 10, 20, 50, 30, 40 }
Find the smallest element starting at index 2:
{ 10, 20, 50, 30, 40 }
And swap it with the element in index 2:
{ 10, 20, 30, 50, 40 }
Find the smallest element starting at index 3:
{ 10, 20, 30, 50, 40 }
And swap it with the element in index 3:
{ 10, 20, 30, 40, 50 }
Finally, find the smallest element starting at index 4:
{ 10, 20, 30, 40, 50 }
And swap it with the element in index 4 (which doesn’t do anything):
{ 10, 20, 30, 40, 50 }
Done!
{ 10, 20, 30, 40, 50 }
Here’s how this algorithm is implemented in C++:
const int nSize = 5;
int anArray[nSize] = { 30, 50, 20, 10, 40 };
// Step through each element of the array
for (int nStartIndex = 0; nStartIndex < nSize; nStartIndex++)
{
// nSmallestIndex is the index of the smallest element
// we've encountered so far.
int nSmallestIndex = nStartIndex;
// Search through every element starting at nStartIndex+1
for (int nCurrentIndex = nStartIndex + 1; nCurrentIndex < nSize; nCurrentIndex++)
{
// If the current element is smaller than our previously found smallest
if (anArray[nCurrentIndex] < anArray[nSmallestIndex])
// Store the index in nSmallestIndex
nSmallestIndex = nCurrentIndex;
}
// Swap our start element with our smallest element
swap(anArray[nStartIndex], anArray[nSmallestIndex]);
}
The most confusing part of this algorithm is the nested loop. The outside loop (nStartIndex) steps through each element one by one. The inner loop (nCurrentIndex) finds the smallest element in the array starting from nStartIndex and sets the variable nSmallestIndex to point to it. The smallest index is then swapped with the start index. Then the outer loop (nStartIndex) advances one element, and the process is repeated.
Quiz
1) Selection sort the following array: { 30, 60, 20, 40, 50, 10 }. Show the array after each swap that takes place.
2) Rewrite the selection sort code above to sort in descending order (largest numbers first). Although this may seem complex, it is actually surprisingly simple.
Quiz solutions
6.5 — Multidimensional Arrays
|
Index
|
6.3 — Arrays and loops
|
6.5 — Multidimensional Arrays
Index
6.3 — Arrays and loops
I am having trouble (a lot) understanding classes; which from what I’ve read so far is crucial to understanding OOP… Any advice?? This tutorial is sweet by the way… Good job…
Jeff, I will be covering classes very shortly, as soon as I wrap up the section on functions. Outside of waiting for those tutorials, my advice (outside of actually purchasing a book) would be to search for “c++ classes” on Google and read everything you can. If you have any specific questions, feel free to post them in my forum and I will do my best to answer them.
hi,,,hope you mind,how can i sort a two dimensional array with series of characters through the use of selection sort method…??
Roseann, I’m not sure what it even means to sort a 2d array. Do you sort each row? Each column? The whole array and then list the results in rows? In columns? Without further information, the problem just doesn’t make sense.
Then what’s the faster and difficult to understand sort?
Will my small mind be able to understand that?
There are a large number of faster sorting algorithms. Two of the more popular faster sorts are quicksort and mergesort. However, sorting algorithms are really the topic for a data structures/algorithms class or tutorial (since they can be implemented in any language), not a C one. :)
See wikipedia for more information.
I didn’t compile this, so I could be wrong, but on line 5, shouldn’t the for loop expression be:
would that be a one off error?
The code was written to follow the 5-element example that proceeds it. You will note the last step in the example is redundant because it will always swap the last element with itself. Similarly, the last iteration of the outer loop will always cause the last element to be swapped with itself!
This doesn’t affect the correctness of the algorithm, it’s just non-optimal. As you note, changing the loop to
nStartIndex < (nSize - 1)removes this non-optimality.Generally when we talk about “off by one” errors, we’re talking about errors that make the algorithm perform incorrectly because the loop executes one too many or too few times. In this case, the algorithm is correct, it just has a redundant step that can be removed by changing that loop condition.
ah, very clear. thanks
hi!!!!!oh please give me some points or idea on how to program the “bubble
sort” which will show all the passes and of course the sorted list inputed by
the user using c looping and array.pls..pls..pls…
tnx
Bubble sort works somewhat similarly to insertion sort. However, it uses a different array access pattern. Bubble sort works by comparing adjacent pairs of elements and swapping them if they are not in the correct order. Thus, it “bubbles” the largest or smallest element to the end of the array. Basically, the algorithm looks like this:
There’s a pretty good description of this algorithm, along with an example, on wikipedia.
Alex, you’re right about the inner nest being confusing! Again, for clarity on my part, I have converted this using while statments. The only part that is still a bit foggy is the incrementing statement in the nested loop. What keeps
in the nested loop from incrementing that loop before the incrementing statement at the bottom of the program
executes and causes the outer to increment? Or is the inner loop incrementing and cycling thru all of the index numbers before the outer loop begins its second loop?
btw: why dont the plus signs show up in the posted code?
int main() { using namespace std; const int nSize = 5; int anArray[nSize] = { 30, 50, 20, 10, 40 }; int nStartIndex = 0; while(nStartIndex < nSize) { int nSmallestIndex = nStartIndex; int nCurrentIndex = nStartIndex plus 1; while(nCurrentIndex < nSize) { if(anArray[nCurrentIndex] < anArray[nSmallestIndex]) nSmallestIndex = nCurrentIndex; nCurrentIndex; } swap(anArray[nStartIndex], anArray[nSmallestIndex]); cout << anArray[nStartIndex] << endl; nStartIndex; } return 0; }The inner loops runs through all it’s iterations before the outer loop is allowed to execute again.
It looks like plus symbols work for the initial response, but if you edit your posts, the AJAX editor seems to be stripping them out.
[ edit: I upgraded to a new version of the AJAX editor and it seems to fix that particular issue. -Alex ]
In the sort example/problem, it would seem that the output statement should read:
But this yields a funky output. The only thing that yields the output below
10
20
30
40
50
Press any key to conitiue…
is this output statement:
Can you elaborate on this a little more? Thanks.
anArray refers to the array itself, and the array variable is really just a pointer. So when you do this:
You’re printing out the address held in anArray pointer (which as you say “yields funky output”)
When you really want is to print the value of the ELEMENTS of anArray. To do that, you need to index the array using the [] operator — in this case, the index is the value of nStartIndex.
Generally speaking, it’s a better idea to sort your array and THEN re-loop through it to print out the sorted result. You could do this by adding the following lines:
for (int nIndex=0; nIndex < nSize; nIndex++) cout << anArray[nIndex] << endl;By the way, the issue with the disappearing + symbols should be fixed now.
C++ is definitely harder than MATLAB, but better in some ways.
The first quiz uses { 30, 60, 20, 40, 50, 10 }, but the answer appears to be using {30 60 20 50 40 10}.
Great tutorial btw