Module 2.2 - For Loops & Nested Loops
In this module, we'll once again be using files within the tar file module2.tar.
The For Loop
The for loop most resembles the while loop, in that it's conditional statement resides before the loop instructions, and is evaluated before the loop statements are performed.
However, it is not only the conditional test that exists in the statement. The number of times that the instructions within a for loop are performed is controled by a variable that changes with each iteration of the loop.
This iteration control variable (Declared at the beginning of the program along with all of the program's variables) is also initialized in this beginning statement of the for loop, as well as how much (And in which direction) to change that variable after each iteration of the loop.
Here is the syntax of the for loop:
for (initial-value; condition; change) {
statement1
statement2
.
.
.
statementn
}
Where:
- initial-value is the initial value of the iteration control variable,
- condition is a boolean statement the determines whether to continue with the loop (if it evaluates to TRUE) or not (when it evaluates as FALSE)
- change is the amount to increase or decrease the iteration control variable
Let's take a look at an example program, factorial.c, inside the week2/LOOP_BASICS directory. This program calculates the factorial for a number input by the user (As you may remember, the factorial of an integer n is
n * (n - 1) * (n - 2) * ... * 1).
1 |
/* This program finds the factorial for a number
input by the user */ |
2 |
#include<stdio.h> |
3 |
|
|
4 |
|
main() { |
5 |
|
|
int i, n, fact; |
6 |
|
|
|
7 |
|
|
printf("Please input a number... "); |
8 |
|
|
scanf("%d", &n); |
9 |
|
|
|
|
|
|
10 |
|
|
/* initialize the factorial variable */ |
11 |
|
|
fact = 1; |
12 |
|
|
|
|
|
|
13 |
|
|
for (i = 1; i <= n ; i++) { |
14 |
|
|
|
fact = fact * i; |
15 |
|
|
} |
16 |
|
|
|
17 |
|
|
printf("\nThe factorial of %d is %d\n", n, fact); |
18 |
|
} |
Everything in the first few lines is pretty standard;
- In lines 1-5, we include the standard input/output library, we start the program with main, and we declare 3 integer variables
- i will be our iteration control variable for the for loop,
- n will be the user input number we find the factorial for, and
- factorial will contain the calculation of factorial).
- In lines 7 & 8, we request and scan in from the user a number for which to calculate the factorial.
- Line 11 initializes our calculation for factorial; the for loop accounts for initializing the iteration control variable, but we are responsible for handling the actual calculations and any initializations associated with that computation.
- Lines 13 through 15 loop over the factorial calculation;
we described the calculation above as n * (n - 1) * ... etc, while our calculation is actually 1 * 2 * 3 *... * n, but they are equivalent.
- Once the iteration variable i becomes greater then n, the for looping condition no longer holds true, the loop terminates, and we print out the value of the factorial and exit the program.
Another program that behaves in a similar fashion to factorial is exponent.c which, predictably, finds the value of m to the nth power, where m and n are input by the user.
Notice that the variable declaration, user input statements, and implementation of the computation via the for loop are identical to factorial.c; the only difference is the computation within the for loop.
Finally, the program for.c is a simple example that just prints out the fact that it's looping, but includes some comments describing it's behavior that you may find helpful. Take a look at this program to get a sense of the fundamental aspects of the for loop without any extraneous computations to get in the way.
Nested Loops
Let's say that we wanted to calculate the factorial, but we wanted to change the program slightly so that it would continually query the user for a new number calculate the factorial for the new input; after each factorial calculation, the program would ask for a new number, and the user would supply one, or input 0 to exit?
In this scenario, a loop structure would need to reside within another loop structure in order to perform the given task. This kind of structure is called a nested loop, and it is useful in numerous programming situations.
In the week2/LOOP_BASICS/NESTED subdirectory, decompressed from the module2.tar file, you'll find 3 examples that serve to show how different flavors of nested loops look.
Let's start with 2nestedfor.c, which, as the name implies, features a for loop nested within another for loop.
1 |
#include<stdio.h> |
2 |
|
|
3 |
|
main() { |
4 |
|
|
int i,j; |
5 |
|
|
int n,m; |
6 |
|
|
|
7 |
|
|
printf("how many outer loops?\n"); |
8 |
|
|
scanf("%d", &n); |
9 |
|
|
|
|
|
|
10 |
|
|
printf("and how many inner loops?\n"); |
11 |
|
|
scanf("%d", &m); |
12 |
|
|
|
|
|
|
13 |
|
|
for (i = 0; i < n ; i++) |
14 |
|
|
|
printf("on OUTER loop %d of %d\n", i + 1, n); |
15 |
|
|
|
|
|
|
16 |
|
|
|
for (j = 0; j < m ; j++) { |
17 |
|
|
|
|
printf("\tinner loop %d of %d\n", j + 1, m); |
18 |
|
|
|
} |
19 |
|
|
} |
20 |
|
} |
- Lines 1 through 3 are pretty standard,
- but things get more interesting in lines 4 & 5. Since we have 2 loops, we need 2 iteration control variables (i & j) and 2 variables for the user input number of outer (n) and inner (m) loops.
- Lines 7 & 8 request and scan in the number of outer loops and store it in the variable n.
- Lines 10 & 11 do the same for the number of inner loops (m).
- Line 13 initiates the outer loop.
- Notice the initial value of i here; we start i out as 0 instead of 1. The initialization of i as 0 is deliberate; even though it forces us to make alterations in the conditional and the printf statement to make things look and work out right, in the future (Specifically, when we get to the Module on Arrays), it will be important to start at 0 rather than 1.
Briefly, arrays contain a sequence of variables. You access each of these variables by refering to it's position in the array; if there are n variables in the array, the sequential numbering starts at 0 and goes through n - 1. And if we wish to access each variable value in the array, we would loop through the array starting at 0 and continuing until n - 1.
- Line 14 prints out the message indicating where we are in the outer loop,
- Line 16 initiates the inner loop. For each iteration of the outer loop, the inner loop will go through all of it's iterations.
- Line 17 prints out the where we are in the inner loop.
- Notice the \t modifier at the beginning of the printf statement here; it prints a tab to start the string output. This will have the effect of indenting each inner loop output string to help differentiate it from the outer loop output.
- Lines 18, 19 & 20 are right curly brackets (or close curlys) that terminate the inner for loop, out for loop, and the program, respectively.
As you can see, 2nestedfor.c does very little, and nests a for loop to do it. Take a look at 3nestedfor.c, which also does very little, and uses an additional nested for loop to do it.
3nestedfor.c is interesting because it shows that we can doubly nest for loops, and that we can double up on the \t tab modifier of printf, which allows us to provide a visualization of the nested-ness of the loops. Compile and run 3nestedfor.c so you can see for yourself.
Moving On
Once we test our knowledge of what's been covered above in the apply section, we'll reflect on some ramifications of iteration control, and we'll extend beyond the relatively content-free examples we've seen so far when we consider some real-world examples such as bisect, which finds where a function crosses the X Axis, and integ_complete.c, which integrates to find the area under a curve with successively greater accuracy based on successively finer slices.
Continue to the Apply Section ->