Topics To Cover

Shortcut #1: for-loops

One of the most common looping situtations you'll come across is this: For example, this program prints out x to the nth power.

power = 1.0;
i = 0;
while (i < n)
{
  power = power * x;
  i = i + 1;
}

If you think the test "i < n" (instead of i <= n) looks strange, note that the variable i starts with 0 instead of 1.

  init;
  while (test-cond)
  {
    statement1
    statement2
          .
          .
    statementk
    update;
  }
Any time we count our way through a loop like this, we'll have three basic pieces of code:
  1. the initialization of our loop counter before the loop begins
  2. the test-condition that determines whether we keep looping
  3. the update (i.e. increment) of our loop counter at the end of each loop iteration
This set-up is so common that C++ has a special syntax allowing us to express it more succinctly, the for loop.
for(init; test-cond; update)
{
  statement1
  statement2
        .
        .
  statementk
}
Applying the above rule, the above while loop can be rewitten as follows using a for loop (drag your mouse for the answer):
 
power = 1.0;
for(int i = 0; i < n; i = i + 1)
{
  power = power * x;
}

The for-loop is just a compact way of writing a while loop which has the three steps outlined above: initialization, test-condition, and update. A for-loop can always be written as a while loop in the following way:

Summary

We usually use for-loops to loop n times. This for-statment will usually look like this:

for(int i = 0; i < n; i++)
{
  ...
}

Shortcut #2: ++ and --

Incrementing (adding 1) and decrementing (subtracting 1) variables is something that goes on all the time in programming. Therefore, C++ has a shortcut: x++ sets x to x + 1, and x-- sets x to x - 1.
Sometimes you want to increment or decrement by values other than one. C/C++ has a nice way of expressing that. The += and -= operators, which are defined like this:
a += b is equivalent to a = a + b
a -= b is equivalent to a = a - b
In fact, for any binary operator we have the operator ℗= defined by
a ℗= b is equivalent to a = a ℗ b
So, for example, if you want to print out all the numbers from 0 to 100 in increments of 5, you might write

for(int i = 0; i <= 100; i += 5)
  cout << i << endl;
The trick here is that while x++ is an expression (its value is the value of x before the increment), it also has a side effect, namely that it changes the value of the variable x. Thus we have:
code fragmentoutput

int k = 5;
cout << k++ << endl;   
cout << k << endl;
5
6
... which may be a little counter-intuitive at first.

For the moment, let's just say this: Don't use ++ and -- in expressions, just use them as standalone statements that provide a shortcut to something like x = x + 1. This is because you have to be careful about which value you get in the expression - is it the value before or after the increment. It's confusing to read such things, and let's just avoid the confusion. Remember, it's not a contest to see who can write a program with the fewest keystrokes! (Though admittedly, that's kind of fun.)

Note: The name C++ is a pun on the ++ operator: It's the C language, incremented!
Note: ++x and --x are also allowed. The difference is that the value of the expression is the value after rather than before the increment/decrement operation.

A Subtle Point of Scope

If you look back at the correspondence between for-loops and while-lops, you'll see that the corresponding while loop is encased in a block of it's own. The point is that any variable you declare in the first slot of the for-statement goes out of scope after you leave the for-loop. Thus, something like:

for(int i = 0; i < 12; i++)
{
  cout << i << endl;
}
cout << i << endl;

shouldn't compile - after all, the i doesn't exist as far as that second cout is concerned. This is usually a nice feature. After all, you only introdced the new variable i to iterative through the numbers 0 up to 11. After you're done with that iteration, there's no point to having i around.

Here's a code that illustrates how that can be nice.


#include <iostream>
using namespace std;

int main()
{
  for(int i = 0; i < 25; i++)
    cout << '*';
  cout << endl << " H E L L O   W O R L D !" << endl;  

  for(int i = 0; i < 25; i++)
    cout << '*';
  cout << endl;

  return 0;
}
See how we didn't need to use a different variable for the two for-loops? That's because their scope does not extend beyond the for-loop itself.

Nested Loops

The body of a loop is a block of code like any other - like the body of "main", or like a then-block or like an else-block. So, that means that it can contain any of the C++ constructs we've talked about so far ... including more loops. Loops inside loops are referred to as "nested". The following chucks of code are equivalent.

Suppose we want to have a program print out a 4x4 square of *'s to the screen.

naive way printing 4x4 squre of *'s elegant way using a nested loop

  // print "*" for 4 times
 
for( int j= 0; j < 4; j++ ) { cout << "*"; } cout << endl;
// print "*" for 4 times
for( int j= 0; j < 4; j++ ) { cout << "*"; } cout << endl;
// print "*" for 4 times
for( int j= 0; j < 4; j++ ) { cout << "*"; } cout << endl;
// print "*" for 4 times
for( int j= 0; j < 4; j++ ) { cout << "*"; } cout << endl;
Of course, we can write a program as on the left. However, it's more elegant to write the program using a nested loop as shown on the right.

Note in code on the right:

  • Each iteration of the outer loop prints a single row.
  • Each iteration of the inner loop prints a single * within that row.

// repeat the blue box 4 times
for( int i = 0; i < 4; i++ )   
{ 
for( int j= 0; j < 4; j++ ) { cout << "*"; } cout << endl;
}

Using break

By default, a loop executes until its condition becomes false. Sometimes, however, it is desirable to immediately exit the body instead. C ++ provides the break statements to to give programmers more flexibility designing the control logic of loops.
Suppose you want to write a program that works as follows:
  • Open a file named "numbers" that contains integers.
  • Add the numbers in the file until seeing a negative number.
With a break statement, we can write a simpler code. In C++, a break statement causes the program to immediately exit from the body of the loop. In our scenario, the program can simply exit the loop as soon as it meets a native number. Therefore, we can simplify the code as follows:

int sum = 0;
int num = 0;
ifstream fin("numbers");

while (fin >> num) 
{
  // Exit the loop if num is negative
  if( num < 0 ) 
    break;
  sum = sum + num;
}

cout << sum << endl;

Mandatory Practice Problems

Other Practice Problems

  1. Write n *'s - this is very easy!
  2. Integration of f(x) by simple end-point approximation - Simple end-point integration approximates the area under a curve between x = 1 and x = b by the sum of n evenly spaced rectangles whose hieghts are the function values at x-values given by the left endpoints of the bases. To remind your self of how this works I've drawn this picture.
  3. A simple example with file io - you'll want to test using the file in4.txt.