Consider the case where we want to find the average test score of a class of students. Using individual variables:
1 2 3 4 5 6 7 8 9 |
const int numStudents = 5; int score0 = 84; int score1 = 92; int score2 = 76; int score3 = 81; int score4 = 56; int totalScore = score0 + score1 + score2 + score3 + score4; double averageScore = static_cast<double>(totalScore) / numStudents; |
That’s a lot of variables and a lot of typing -- and this is just 5 students! Imagine how much work we’d have to do for 30 students, or 150.
Plus, if a new student is added, a new variable has to be declared, initialized, and added to the totalScore calculation. Any time you have to modify old code, you run the risk of introducing errors.
Using arrays offers a slightly better solution:
1 2 3 4 |
const int numStudents = 5; int scores[numStudents] = { 84, 92, 76, 81, 56 }; int totalScore = scores[0] + scores[1] + scores[2] + scores[3] + scores[4]; double averageScore = static_cast<double>(totalScore) / numStudents; |
This cuts down on the number of variables declared significantly, but totalScore still requires each array element be listed individually. And as above, changing the number of students means the totalScore formula needs to be manually adjusted.
If only there were a way to loop through our array and calculate totalScore directly.
Loops and arrays
In a previous lesson, you learned that the array subscript doesn’t need to be a constant value -- it can be a variable. This means we can use a loop variable as an array index to loop through all of the elements of our array and perform some calculation on them. This is such a common thing to do that wherever you find arrays, you will almost certainly find loops! When a loop is used to access each array element in turn, this is often called iterating through the array.
Here’s our example above using a for loop:
1 2 3 4 5 6 7 8 9 |
const int numStudents = 5; int scores[numStudents] = { 84, 92, 76, 81, 56 }; int totalScore = 0; // use a loop to calculate totalScore for (int student = 0; student < numStudents; ++student) totalScore += scores[student]; double averageScore = static_cast<double>(totalScore) / numStudents; |
This solution is ideal in terms of both readability and maintenance. Because the loop does all of our array element accesses, the formulas adjust automatically to account for the number of elements in the array. This means the calculations do not have to be manually altered to account for new students, and we do not have to manually add the name of new array elements!
Here’s an example of using a loop to search an array in order to determine the best score in the class:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
#include <iostream> int main() { const int numStudents = 5; int scores[numStudents] = { 84, 92, 76, 81, 56 }; int maxScore = 0; // keep track of index of our largest score for (int student = 0; student < numStudents; ++student) if (scores[student] > maxScore) maxScore = scores[student]; std::cout << "The best score was " << maxScore << '\n'; return 0; } |
In this example, we use a non-loop variable called maxScore to keep track of the highest score we’ve seen. maxScore is initialized to 0 to represent that we have not seen any scores yet. We then iterate through each element of the array, and if we find a score that is higher than any we’ve seen before, we set maxScore to that value. Thus, maxScore always represents the highest score out of all the elements we’ve searched so far. By the time we reach the end of the array, maxScore holds the highest score in the entire array.
Mixing loops and arrays
Loops are typically used with arrays to do one of three things:
1) Calculate a value (e.g. average value, total value)
2) Search for a value (e.g. highest value, lowest value).
3) Reorganize the array (e.g. ascending order, descending order)
When calculating a value, a variable is typically used to hold an intermediate result that is used to calculate the final value. In the above example where we are calculating an average score, totalScore holds the total score for all the elements examined so far.
When searching for a value, a variable is typically used to hold the best candidate value seen so far (or the array index of the best candidate). In the above example where we use a loop to find the best score, maxScore is used to hold the highest score encountered so far.
Sorting an array is a bit more tricky, as it typically involves nested loops. We will cover sorting an array in the next lesson.
Arrays and off-by-one errors
One of the trickiest parts of using loops with arrays is making sure the loop iterates the proper number of times. Off-by-one errors are easy to make, and trying to access an element that is larger than the size of the array can have dire consequences. Consider the following program:
1 2 3 4 5 6 7 8 |
const int numStudents = 5; int scores[numStudents] = { 84, 92, 76, 81, 56 }; int maxScore = 0; // keep track of our largest score for (int student = 0; student <= numStudents; ++student) if (scores[student] > maxScore) maxScore = scores[student]; std::cout << "The best score was " << maxScore << '\n'; |
The problem with this program is that the conditional in the for loop is wrong! The array declared has 5 elements, indexed from 0 to 4. However, this array loops from 0 to 5. Consequently, on the last iteration, the array will execute this:
1 2 |
if (scores[5] > maxScore) maxScore = scores[5]; |
But scores[5] is undefined! This can cause all sorts of issues, with the most likely being that scores[5] results in a garbage value. In this case, the probable result is that maxScore will be wrong.
However, imagine what would happen if we inadvertently assigned a value to array[5]! We might overwrite another variable (or part of it), or perhaps corrupt something -- these types of bugs can be very hard to track down!
Consequently, when using loops with arrays, always double-check your loop conditions to make sure you do not introduce off-by-one errors.
Quiz
1) Print the following array to the screen using a loop:
1 2 |
const int arrayLength(9); int array[arrayLength] = { 4, 6, 7, 3, 8, 2, 1, 9, 5 }; |
2) Given the array in question 1:
Ask the user for a number between 1 and 9. If the user does not enter a number between 1 and 9, repeatedly ask for a number until they do. Once they have entered a number between 1 and 9, print the array. Then search the array for the number that the user entered and print the index of that element.
You can test std::cin for invalid input by using the following code:
1 2 3 4 5 6 |
// if the user entered something invalid if (std::cin.fail()) { std::cin.clear(); // reset any error flags std::cin.ignore(32767, '\n'); // ignore any characters in the input buffer } |
3) Modify the following program. Rename maxScore to maxIndex, and have it hold the index of the largest score rather than the actual last score.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
#include <iostream> int main() { const int numStudents(5); int scores[numStudents] = { 84, 92, 76, 81, 56 }; int maxScore = 0; // keep track of our largest score for (int student = 0; student < numStudents; ++student) if (scores[student] > scores[maxIndex]) maxScore = scores[student]; std::cout << "The best score was " << maxScore << '\n'; return 0; } |
Quiz solutions
![]() |
![]() |
![]() |
I was under the impression I was supposed to print the array of numbers that the user gave as input instead of the given array in the example. Probably it is better do use do while loops instead of my solution, but this is what I came up with (unfortunately it seems "<<" and include iostream seems to be messed up by the post):
#include
int main(int argc, const char * argv[])
{
using namespace std;
int anInputNumbers[200]={0};
int nCorrectInputIdx;
for (int iii=0;iii<200;iii++){
cout <> anInputNumbers[iii];
if (anInputNumbers[iii]>=0 && anInputNumbers[iii] <=9){
nCorrectInputIdx=iii;
cout << "The numbers you entered were:" << endl;
for (int jjj=0;jjj<=iii;jjj++)
cout << anInputNumbers[jjj] << " ";
cout << endl << "You managed to enter a correct number on try " << nCorrectInputIdx+1 << endl;
break;
}
}
return 0;
}
#include <iostream>
int main(int argc, const char * argv[])
{
using namespace std;
int anInputNumbers[200]={0};
int nCorrectInputIdx;
for (int iii=0;iii<200;iii++){
cout << "Enter a number between 0-9: ";
cin >> anInputNumbers[iii];
if (anInputNumbers[iii]>=0 && anInputNumbers[iii] <=9){
nCorrectInputIdx=iii;
cout << "The numbers you entered were:" << endl;
for (int jjj=0;jjj<=iii;jjj++)
cout << anInputNumbers[jjj] << " ";
cout << endl << "You managed to enter a correct number on try " << nCorrectInputIdx+1 << endl; // index plus one to get the number of tries
break;
}
}
return 0;
}
hi iam just a student and i cannot answer this quiz can you help me; please?
4.2 Determine the score
Your friend has developed a game in which you have a
player that walks in a maze and kills his enemies. He
has a problem in calculating his score. He asked you to
write a program that prints his score.
You will be given: 2 Integers M and N (1<= M <= N
<= 100) followed by a 2D representation of the maze
(M X N), where the point [i, j] represents the value of
killing the monster on this grid.
The path that the player will take: string which points
the direction you move to ( N for North, W for West, E
for East, S for South )
The player's starting point is [0, 0]
Print the score of the player.
Sample Input :-
5 5
1 2 3 4 5
6 5 4 3 2
5 8 5 2 9
1 3 4 9 7
6 5 4 3 2
SSESEN
Sample Output :-
32
hay,
first of all thanks a lot for this tutorial :)
now i have a simple problem, when i try to do the second Quiz
if I entered char for example $
it enter an infinite loop
int anArray[9] = { 4, 6, 7, 3, 8, 2, 1, 9, 5 };
int num;
do
{
cout <> num;
}
while(num 9);
for(int nIndex =0; nIndex < sizeof(anArray)/sizeof(anArray[0]);nIndex++)
if(anArray[nIndex] == num)
{
cout << "Your array index is : " << nIndex <<endl;
break;
}
I guess it's better to use sizeof(anScores) instead of nNumStudents=5 :)
For 6.3 — Arrays and loops - 2nd Quiz: If I run your code, and enter any letter instead of a number, it loops infinitely on printing the request. Why? (Entering any number other than 1..9 it works instead: it properly stops on asking)
cant paste my code properly sorry
is my solution same on #2?
#include
using namespace std;
void main()
{
int number;
do
{
cout <> number;
}
while(number 9);
int array[] = {1,3,2,5,8,11,4,9,21,24};
for (int index = 0; index <= 9; index++)
{
cout << array[index] << " ";
}
cout << endl << number << " has index " << array[number] << endl;
system("pause");
}
#include
using namespace std;
void main()
{
int number;
do
{
cout <> number;
}
while(number 9);
int array[] = {1,3,2,5,8,11,4,9,21,24};
for (int index = 0; index <= 9; index++)
{
cout << array[index] << " ";
}
cout << endl << number << " has index " << array[number] << endl;
system("pause");
}