Program Flow Controls: Hapter Hree

You might also like

Download as pdf or txt
Download as pdf or txt
You are on page 1of 33

Fundamentals of Programming I

CHAPTER THREE
Program Flow Controls
3.1 Introduction
A running program spends all of its time executing instructions or statements in that program.
The order in which statements in a program are executed is called flow of that program.
Programmers can control which instruction to be executed in a program, which is called flow
control. The process of performing one statement after another is called the flow of execution or
flow of control. The term flow control reflects the fact that the currently executing statement has
the control of the CPU, which when completed will be handed over (flow) to another statement.

Flow control in a program is typically sequential, which is the most common and straight-
forward, where programming statements are executed in the order that they are written - from top
to bottom in a sequential manner. But a program is usually not limited to a linear sequence of
instructions. During its process the program will have an execution that might be divided to other
paths by branching statements. Or perform a block of statement repeatedly until a condition
fails by Repetition or looping.

Flow control is an important concept in programming because it will give all the power to the
programmer to decide what to execute during a run and what is not, therefore, affecting the
overall outcome of the program. Shortly it is a way to alter the natural sequence of execution in a
program. In other words, they act as “direction signals” to control the path a program takes. For
that purpose, C++ provides control structures that serve to specify what has to be done by our
program, when and under which circumstances.

There are three basic flow control constructs - sequential, conditional (or decision),
and loop (or iteration), as illustrated below.

Department of Software Engineering, AASTU Page 1


Fundamentals of Programming I

3.2 Revision on Block Statements


With the introduction of control structures we are going to have to introduce a new concept: the
compound-statement or block. A block is a group of statements which are separated by
semicolons (;) like all C++ statements, but grouped together in a block enclosed in braces: { }:

statement1;

statement2;

statement3;

From the compiler’s perspective, a block statement is equivalent to a single statement. Block
statements can be nested inside other block statements

Most of the control structures that we will see in this section require a generic statement as part
of its syntax. A statement can be either a simple statement (a simple instruction ending with a
semicolon) or a compound statement (several instructions grouped in a block), like the one just
described. In the case that we want the statement to be a simple statement, we do not need to
enclose it in braces ({}). But in the case that we want the statement to be a compound statement
it must be enclosed between braces ({}), forming a block.

3.3 Conditional (Decision) Flow Control


The control statements that allow alternative actions based up on conditions that are evaluated at
run time are generally called decision or selection statements. These include the following type
of conditionals,

 if statement,

 if --- else statement,

 else if statement (if ---- else if--- . . . . --- else)

 switch-case

 conditional expression

Department of Software Engineering, AASTU Page 2


Fundamentals of Programming I
1) The If statement
It is sometimes desirable to make the execution of a statement dependent upon a condition being
satisfied. The if statement provides a way of expressing this and allows for conditional execution.
The statement that is included within it will be executed only if its condition is true (i.e. the if
keyword is used to execute a statement or block only if a condition is fulfilled).

The syntax for the simple if statement is:

if (expression) // boolean expression


{
statement (s);
}
next statement(s);

 The expression must produce a Boolean value, either true or false

 If expression returns true, the statement or the block is executed and then next statement(s)
get executed.

 If expression returns false, the statement or the block is not executed and the program
continues at execution of next statement(s).

For example, let us examine the pseudocode statement given below:

If student’s grade is greater than or equal to 60

Print “Passed”

This pseudocode determines whether the condition "student’s grade is greater than or equal to
60" is true or false. If the condition is true, then "Passed" is printed and the next pseudocode
statement in order is "performed" (remember that pseudocode is not a real programming
language). If the condition is false, the print statement is ignored and the next pseudocode
statement in order is performed. Note that the second line of this selection structure is indented.
Such indentation is optional, but it is highly recommended because it emphasizes the inherent
structure of structured programs.

The preceding pseudocode If statement can be written in C++ as follow:

if ( grade > = 6 0 )
cout<<" Passed " ;

Department of Software Engineering, AASTU Page 3


Fundamentals of Programming I
Remember that if we want more than a single statement to be executed in case that the condition
is true, we must group them in a block by enclosing them in braces { }.

Example:
1 if (mark >= 50) {
2 cout << "Congratulation!" << endl;
3 cout << "Keep it up!" << endl;
4
}
5

2) The If…else statement


The basic “if” statement can be extended by adding the “else” clause (i.e. we can additionally
specify what we want to happen if the condition is not fulfilled by using the keyword else). The
if …else statement works the same as the if statement except that it allows the programmer to
specify an action to perform when the condition is true and a different action to perform when
the condition is false.

The syntax for the if ….else statement is:

if (expression){
statement1 / block1
}
else{
statement2 / block2;
}
next statement(s);

Again here also, the (expression) must produce a Boolean value

 If (expression) returns true, statement1/block1 is executed and then next statement(s) is


executed. Otherwise statement2/block2 is executed and then next statement(s) is executed.

For example, the following code fragment prints Congratulation! and keep it up! on separate line
only if the value stored in the mark variable is greater than or equal to 50:
1 if (mark >= 50) { Note:
2 cout << "Congratulation!" << endl; You could omit races { }, if there is only
3 cout << "Keep it up!" << endl; one statement inside block. However, it
4 } recommendable to keep the braces, even
else { though there is only one statement in the
cout << "Try Harder!" << endl; block, to improve the readability of your
} program.

Department of Software Engineering, AASTU Page 4


Fundamentals of Programming I
(3) Conditional Expression Operator
A conditional expression operator (discussed in chapter 2) is used for abbreviating simple if …
else statements. A conditional operator is a ternary (3-operand) operator, in the form of

boolean_Expression ? Expression1 : Expression2;

Depending on the evaluation of boolean_Expression, it returns the value of Expression1


or Expression2.

Example 1:
int num1 = 5, num 2 = 6, min, max;
min = num1 < num2 ? num1 : num2 // returns min = 5
max = num1 < num2 ? num1 : num2 // returns max = 6

Example 2:
cout << mark >= 50 ? "PASS" : "FAIL" << endl;
// return either "PASS" or "FAIL", and put to cout stream

4) Nested if/else selection structure


Like compound statements, selection statements can be used wherever any other statement can
be used. So a selection statement can be used within another selection statement. This is called
nesting statements.

When if..else statements are nested, the compiler uses the following rule to parse the compound
statement:
Match each else with the last unmatched if.

A frequently-used form of nested if statements involves the else part consisting of another if-else
statement. For example: nested if…else statements to check if a character is a digit, upper letter,
lower letter or special character:
if (ch >= '0' && ch <= '9')
kind = digit;
else {
if (ch >= 'A' && ch <= 'Z')
kind = upperLetter;
else {
if (ch >= 'a' && ch <= 'z')
kind = lowerLetter;
else
kind = special;
}
}

Department of Software Engineering, AASTU Page 5


Fundamentals of Programming I
5) The If … else if statement combination
The if … else statement allows for conditional execution based up on two alternatives. If you
have more than two possible alternatives, you can link together a sequence of if … else
statements. This construction is called if … else if statement.

Nested if … else statements are often used to test a sequence of parallel alternatives, where only
the else clauses contain further nesting. In that case, the resulting compound statement is usually
formatted by lining up the else if phrases to emphasize the parallel nature of the logic.

Here is an example of if …else … if statements:

if (mark >= 80)


{
cout << "A" << endl;
}
else if (mark >= 70) Question:
{  What is the difference between
cout << "B" << endl; nested if – else and else if
} selection structure? Explain
else if (mark >= 60) your answer with example.
{
cout << "C" << endl;
}
else if (mark >= 50)
{
cout << "D" << endl;
}
else
{
cout << "F" << endl;
}

Department of Software Engineering, AASTU Page 6


Fundamentals of Programming I
6) The Switch statement
The switch statement is similar to if … else if combination, it enables you to test several cases
generated by a given expression. But it is more specialized because it requires that the conditions
that determine the alternatives have the form (var = = const), where var is a variable and const is
a literal constant.

The switch statement has four components: Switch, Case, Default, Break, where Default and
Break are Optional.

The syntax is:


switch (expression)
{
case constant-1:
group of statements 1;
break;
case constant-2:
group of statements 2;
break;
case constant-3:
group of statements 3;
break;
-
-
default:
default group of statements
}

The switch statement works in the following way:


 First expression (called the switch tag) is evaluated, and the outcome is compared to each
of the literal constants (called case labels), in the order they appear, until a match is found.
Note that the expression must produce a result of type char, byte, short or int, but not long,
float, or double.

 When match is found the group of statements following the matching case is then executed
until it finds the break statement. When it finds this break statement the program jumps to
the end of the switch selective structure. The break; statement tells the computer to exit the
switch statement

 Finally, if the value of expression did not match any of the previously specified case values
(you can include as many case labels as values you want to check), the program will
execute the statements included after the default case, if it exists (since it is optional).
Department of Software Engineering, AASTU Page 7
Fundamentals of Programming I
Both of the following code fragments have the same behavior:
switch example if-else equivalent
switch (x) { if (x == 1) {
case 1: cout << "x is 1";
cout << "x is 1"; }
break; else if (x == 2) {
case 2: cout << "x is 2";
cout << "x is 2";
break; }
default: else {
cout << "value of x unknown"; cout << "value of x unknown";
} }

The switch statement is a bit peculiar within the C++ language because it uses labels instead of
blocks. This forces us to put break statements after the group of statements that we want to be
executed for a specific condition. Otherwise the remainder statements including those
corresponding to other labels will also be executed until the end of the switch selective block or a
break statement is reached.

For example, suppose we have parsed a binary arithmetic operation into its three components
and stored these in variables operator, operand1, and operand2. The following switch statement
performs the operation and stores the result in result.

switch (operator) {
case '+': result = operand1 + operand2;
break;
case '-': result = operand1 - operand2;
break;
case '*': result = operand1 * operand2;
break;
case '/': result = operand1 / operand2;
break;
default: cout << "unknown operator: " << ch << '\n';
break;
}

As illustrated by this example, if we did not include a break statement after the first group for
case one, the program will not automatically jump to the end of the switch selective block rather
it would continue executing the rest of statements until it reaches either a break instruction or the
end of the switch selective block.

Department of Software Engineering, AASTU Page 8


Fundamentals of Programming I
The use of break statement makes unnecessary to include braces {} surrounding the statements
for each of the cases, and it can also be useful to execute the same block of instructions for
different possible values for the expression being evaluated.

Even if it is usually necessary to include a break statement at the end of each case, there are,
however, situations in which it makes sense to have a case without a break. For example, if we
extend the above statement to also allow x (both lower and upper case) to be used as a
multiplication operator, we will have:
switch (operator) {
case '+': result = operand1 + operand2;
break;
case '-': result = operand1 - operand2;
break;
case 'x':
case 'X':
case '*': result = operand1 * operand2;
break;
case '/': result = operand1 / operand2;
break;
default: cout << "unknown operator: " << ch << '\n';
break;
}

Because case 'x' and case ‘X’ has no break statement (in fact no statement at all!), when this case is
satisfied, execution proceeds to the statements of the next case and the multiplication is
performed.

It should be obvious that any switch statement can also be written as multiple if-else statements.
So that the above statement, for example, may be written as:
if (operator == '+')
result = operand1 + operand2;
else if (operator == '-')
result = operand1 - operand2;
else if (operator == 'X' || operator == 'x' || operator == '*')
result = operand1 * operand2;
else if (operator == '/')
result = operand1 / operand2;
else
cout << "unknown operator: " << ch << '\n';

Notice that switch can only be used to compare an expression against constants. Therefore we
cannot put variables as labels (e.g. case n: where n is a variable) or ranges like case (1. .3):
because they are not valid C++ constants. If you need to check ranges or values that are not
constants, use a concatenation of if ... else if statements.
In general, preference should be given to the switch version when possible. The if-else
approach should be reserved for situation where a switch cannot do the job.

Department of Software Engineering, AASTU Page 9


Fundamentals of Programming I

3.4 Looping
In general, statements are executed sequentially; the first statement in a function is executed first,
followed by the second, and so on. However, there may be a situation, when you need to execute
a block of code several times - looping. Such programming statements are called loops, because
the flow of execution “loops back” to the beginning of the block.

A loop statement allows us to execute a statement or group of statements multiple times and
following is the general from of a loop statement in most of the programming languages:

There are two essentially different ways of knowing when a loop has been repeated enough times.

a) When you know exactly how many loops you want to make.

 Repeat a statement or block a specified number of times

 This type of loop is called COUNT-CONTROLLED LOOPS.

 Count-controlled loops contain

o An initialization of the loop control variable which is a special variable to keep


track of the number of times the loop has been executed. Such a variable called
a counter.

o The counter is increased by a fixed amount (usually by 1) each time the loop is
executed.

o An expression to test if the proper number of repetitions has been completed


o An update of the loop control variable to be executed with each iteration of the body.

 An example of this would be if you wished this program to print the word Hello
exactly 7 times.

Department of Software Engineering, AASTU Page 10


Fundamentals of Programming I
b) When some conditions has been fulfilled

 Repeat a statement or block until a condition within the loop body changes that cause the
repetition to stop.

 We will call this kind of loops Condition-Loop or Event-controlled loops.

 Types of Event-Controlled Loops

o Sentinel controlled: Keep processing data until a special value (sentinel value)
that is not a possible data value is entered to indicate that processing should stop.

o End-of-file controlled: Keep processing data or executing statement(s) as long as


there is more data in the file.

o Flag controlled: Keep processing data until the value of a flag changes in the
loop body.

C++ programming language provides the following types of loop to handle looping
requirements.
1. The for loop
2. The while loop
3. The do … while loop

(1) The For loop


The for statement (also called for loop) is similar to the while statement, but has two additional
components: an expression which is evaluated only once before everything else, and an
expression which is evaluated once at the end of each iteration. The general form of the for
statement is:

for (initialization_expression; loop_condition; increment_expression)


{
//block of statements
}

The control of the for loop appear in parentheses and is made up of three parts.

 The first part, the initialization_expression, used to declare and/or initialize control
variable(s) (i.e. sets the initial conditions) for the loop, particularly the loop counter. It is
evaluated first, before any iteration occurs for the loop. Also executed only once.

Department of Software Engineering, AASTU Page 11


Fundamentals of Programming I
 The loop_condition (which must be an expression having the value true or false) is used
to determine whether the loop should continue iterating; it is evaluated immediately after
the initialization; if it is true, the statement is executed. This expression is checked at the
beginning of every loop iteration, and when it is false, execution continues the statement
following the loop block.

 The third part of the control information, the increment_expression also called update
expression, is usually used to increment the loop counter (i.e. to update the control
variable(s)). This is executed at the end of each loop iteration and its main function is to
repeat statement while condition remains true.

 Block of statement is any executable set of statements.

Note that the for loop provides specific locations to contain an initialization statement and an
increase statement. So this loop is specially designed to perform a repetitive action with a
counter which is initialized and increased on each iteration.

Generally the for loop works in the following way:

1. Firstly initialization is executed.

2. Next the condition is checked. If it is true the loop continues, otherwise the loop ends and
statement is skipped (not executed).

3. Statement is executed. As usual, it can be either a single statement or a block enclosed in


braces { }.

4. Evaluate update expression:- whatever is specified in the increase field is executed.

5. Finally, the loop gets back to step 2 and repeat through step 4.

Department of Software Engineering, AASTU Page 12


Fundamentals of Programming I
The most common use of for loops is for situations where a variable is incremented or
decremented with every iteration of the loop.

The following for loop, for example, countdown start from 10 up to 1 and also calculates the sum
of all integers from 1 to n.

// countdown using a for loop 10, 9, 8, 7, 6, 5, 4, 3, 2, 1,


#include <iostream.h>
FIRE!
int main (){
for (int n=10; n>0; n--)
{ Enter a positive integer: 100
cout << n << ", "; The sum of the first: 100
} integers is 5050
cout << "\nFIRE!\n";

int n;
cout << "Enter a positive integer: ";
cin >> n;
long sum=0;

for (int i=1; i <= n; i++)


{
sum += i;
cout<<"The sum of the first: "<<n
<<" integers is "<<sum <<’\n’;
}
return 0;
}

Any of the three expressions in a for loop may be empty; especially the initialization and update
expression are optional. They can remain empty, but in all cases the semicolon signs between
them must be written.

For example we could write:

for ( ;n < 10; ) if we wanted to specify no initialization and no update expression

if we wanted to include an update expression but no initialization


for (; n<10; n++)
(maybe because the variable was already initialized before).

for (;;) infinite loop:- Removing all the expressions gives us an infinite loop

Department of Software Engineering, AASTU Page 13


Fundamentals of Programming I
A for loop can have more than one loop variable set up during the initialization section (part one)
and more than one update expression in the change section (part three). In such cases, by using
the comma operator (,) we can specify and separate more than one expression in initialization
and update section of the for loop. The comma operator (,) is an expression separator, it serves to
separate more than one expression where only one is generally expected.

For example, suppose that we wanted to initialize more than one variable in our loop:

This loop will execute for 50 times if neither n or i are modified within the loop. In this loop
statement n starts with a value of 0, and i with 100, the condition is n!=i (i.e. n is not equal to i).
Because n is increased by one and i decreased by one, on every iteration of the loop; the
condition expression will become false after the 50th loop, when both n and i will be equal to 50.

Look at to another example below

for(i=0, j=0; i*j<1000; i++, j+=2)


{
cout<<i<<” * ”<<j<<“ = “<<i*j;
}

Because loops are statements, they can appear inside other loops. In other words, loops can be
nested. For example,
for (inti = 1; i<= 3; ++i)
{
for (int j = 1; j <= 3; ++j)
{
cout << '(' << i << ' , ' << j << ") : ";
}
}

The above code segment produces the product of the set {1, 2, 3} with itself, giving the output:

(1 , 1) : (1 , 2) : (1 , 3) : (2 , 1) : (2 , 2) : (2 , 3) : (3 , 1) : (3 , 2) : (3 , 3)

Department of Software Engineering, AASTU Page 14


Fundamentals of Programming I

Scope of variables
int main(){
int n;
cout << "Enter a positive integer: ";
cin >> n;
long sum=0; //global variable
for (int i = 1; i < n/2; i++) // the scope of this i is this loop
{
sum += i;
for (int i = n/2; i <= n; i++) // the scope of this i is this loop
{
sum += i;
cout << "The sum of the first " << n << " integers is "<< sum << endl;
}
}
}

Examples:
a) This program finds the maximum of a sequence of input numbers using a Sentinel to Control
a for Loop:
int main(){
int n, max;
cout << "Enter positive integers (0 to quit): ";
cin >> n;
for (max = n; n > 0; ){
if (n > max) max = n;
cin >> n;
}
cout << "max = " << max << endl;
}

b) Using a Flag to Break Out of a Nest of Loops


int main(){
const int N=5;
bool done=false;
for (int i=0; i<N; i++){
for (int j=0; j<N && !done; j++){
for (int k=0; k<N && !done; k++){
if (i+j+k>N) done = true;
else cout << i+j+k << " ";
}
cout << "* ";
}
cout << "." << endl; // inside the i loop, outside the j loop
done = false;
}
}

Department of Software Engineering, AASTU Page 15


Fundamentals of Programming I
(2) The while loop
The while statement (also called while loop) provides a way of repeating a statement while a
condition holds. It is one of the three flavors of iteration in C++. The general syntax and form of
the while statement is look as follow:

while (expression)
{
//statement(s)
}

In this case, the expression (called the loop condition) is evaluated and then statement(s) (called
the loop body) is executes as long as this given logical expression between parentheses is true
(i.e. the outcome is nonzero) and the whole process is repeated. Otherwise, the loop is terminated
(i.e. when expression is false, execution continues with the statement following the loop block).

Note that the expression is tested at the beginning of the loop, so if it is initially false, the loop
will not be executed at all.

For example, we are going to make a program to countdown using a while-loop:


// custom countdown using while Enter the starting number > 8
#include <iostream.h> 8, 7, 6, 5, 4, 3, 2, 1, FIRE!
void main (){
int n;
cout << "Enter the starting number >
";
cin >> n;
while (n>0) {
cout << n << ", ";
--n;
}
cout << "FIRE!\n";
}

Department of Software Engineering, AASTU Page 16


Fundamentals of Programming I
In the example program above, when the program starts the user is prompted to insert a starting
number for the countdown. Then the while loop begins, if the value entered by the user fulfills
the condition n > 0 (that n is greater than zero) the block that follows the condition will be
executed and repeated while the condition (n > 0) remains being true.

The whole process of the previous program can be interpreted according to the following script
(beginning in main):

1. User assigns a value to n


2. The while condition is checked (n>0). At this point there are two possibilities:
 If condition is true: statement is executed (to step 3)
 else if condition is false: ignore statement and continue after it (to step 5)
3. Execute statement: //prints the value of n on the screen and decreases n by 1
cout << n << ", ";
--n;
4. End of block. Return automatically to step 2
5. Continue the program right after the block: print FIRE! and end program.

When creating a while-loop, we must always consider that it has to end at some point, therefore
we must provide within the block some method to force the condition to become false at some
point, otherwise the loop will continue looping forever. In this case we have included --n; that
decreases the value of the variable that is being evaluated in the condition (n) by one, and this
will eventually make the condition (n>0) to become false after a certain number of loop
iterations: to be more specific, when n becomes 0, that is where our while-loop and our
countdown end.

Of course this is such a simple action for our computer that the whole countdown is performed
instantly without any practical delay between numbers.

Another example, suppose we wish to calculate the sum of all numbers from 1 to some integer
denoted by n. This can be expressed as:

i = 1;
sum = 0;
while (i <= n){
sum += i;
++i;
}

Department of Software Engineering, AASTU Page 17


Fundamentals of Programming I
In example program above, for n set to 10, the below table provides a trace of the loop by listing
the values of the variables involved and the loop condition.

Table 3.1: While loop trace

Iteration i n i <= n sum += i ++i

1st 1 5 true 1 2
2nd 2 5 true 3 3
3rd 3 5 true 6 4
4th 4 5 true 10 5
5th 5 5 true 15 6
6th 6 5 true 21 7
7th 7 true 28 8
8th 8 true 36 9
9th 9 true 45 10
10th 10 true 55 11
11th 11 false

It is not unusual for a while loop to have an empty body (i.e., a null statement). The following
loop, for example, sets n to its greatest odd factor.

int n = 40; int n = 40;


while (n=n/2, cout << n<<"\n" && n%2==0) while (n=n/2, cout << n<<"\n" && n%2==0)
{ ;
} cout << n<<"\n"
cout << n<<"\n"

Here the loop condition provides all the necessary computation, so there is no real need for a
body. The loop condition not only tests that n is even, it also divides n by two, display the value
of n on screen and ensures that the loop will terminate should n be zero.

Note: if you do not put the either curly brace (i.e. {}) or semicolon (;) after while loop as shown
on the example above to indicate that the loop have an empty body it will automatically execute
the statement after it repeatedly until the loop condition get false.

Department of Software Engineering, AASTU Page 18


Fundamentals of Programming I
(3) The Do … while loop
The do statement (also called do loop) is similar to the while statement, except that its body is
executed first and then the loop condition is examined after the execution of statement instead of
before, granting at least one execution of statement even if condition is never fulfilled. The
general form of the do statement is:

do{
statement(s);
}while(expression);

First statement(s) is executed and then expression is evaluated. If the outcome of the expression
is nonzero then the whole process is repeated. Otherwise, the loop is terminated.

The do loop is less frequently used than the while loop. It is useful for situations where we need
the loop body to be executed at least once, regardless of the loop condition. For example,
suppose we wish to repeatedly read a value and print its square, and stop when the value is zero.
This can be expressed as the following loop:

// square number printer Enter number (0 to end): 12


#include <iostream.h> Square of the number:: 144
int main () Enter number (0 to end): 16
{ Square of the number:: 256
unsigned long n; Enter number (0 to end): 0
do { You entered: 0
cout << "Enter number (0 to end): ";
cin >> n;
cout << "Square of the number: " << n*n << "\n";
} while (n != 0);
return 0;
}

Department of Software Engineering, AASTU Page 19


Fundamentals of Programming I
The do-while loop is usually used when the condition that has to determine the end of the loop is
determined within the loop statement itself, like in the previous case, where the user input within
the block is what is used to determine if the loop has to end. In fact if you never enter the value 0
in the previous example you can be prompted for more numbers forever.

The difference between while loop and do-while loop lies in the order of the body and condition.
In while-do, the condition is tested first. The body will be executed if the condition is true and
the process repeats. In do-while, the body is executed and then the condition is tested. Take note
that the body of do-while will be executed at least once (vs. possibly zero for while-do).

Suppose that your program prompts user for a number between 1 to 10, and checks for valid
input, do-while with a Boolean flag could be more appropriate.

// Input with validity check


bool valid = false;
int number;
do {
// prompt user to enter an int between 1 and 10
......
// if the number entered is valid, set done to exit the loop
if (number >=1 && number <= 10) {
valid = true;
}
} while (!valid); // Need a semi-colon to terminate do-while

Below is an example of using while-do:

// Game loop
bool gameOver = false;
while (!gameOver) {
// play the game
......
// Update the game state
// Set gameOver to true if appropriate to exit the game loop
......
}

Unlike the while loop, the do...while loop is never used in situations where it would have a null
body. Although a do...while loop with a null body would be equivalent to a similar while loop,
the latter is always preferred for its superior readability.

Department of Software Engineering, AASTU Page 20


Fundamentals of Programming I
Example (Counter-Controlled Loop):
Prompt user for an upper bound. Sum the integers from 1 to a given upper bound and compute its
average.

// Sum from 1 to a given upperbound and compute their average (SumNumbers.cpp)


#include <iostream>
using namespace std;

int main()
{
int sum = 0; // Store the accumulated sum
int upperbound;
cout << "Enter the upperbound: ";
cin >> upperbound;

// Sum from 1 to the upperbound


for (int number = 1; number <= upperbound; ++number)
{
sum += number;
}
cout << "Sum is " << sum << endl;
cout << "Average is " << (double)sum / upperbound << endl;

// Sum only the odd numbers


int count = 0; // counts of odd numbers
sum = 0; // reset sum
for (int number=1; number <= upperbound; number=number+2)
{
++count;
sum += number;
}
cout << "Sum of odd numbers is " << sum << endl;
cout << "Average is " << (double)sum / count << endl;

Department of Software Engineering, AASTU Page 21


Fundamentals of Programming I
Example (Sentinel-Controlled Loop):
Prompt user for positive integers, and display the count, maximum, minimum and average.
Terminate when user enters -1.

/* Prompt user for positive integers and display the count, maximum,
minimum and average. Terminate the input with -1 (StatNumbers.cpp) */
#include <iostream>
#include <climits> // for INT_MAX
#include <iomanip> // for setprecision(n)
using namespace std;
int main() {
int numberIn; // input number (positive integer)

// count of inputs, sum of inputs, max of inputs respectively and initialized to 0


int count = 0, sum = 0, max = 0;

int min = INT_MAX; // min of inputs, init to maximum (need <climits>)


int sentinel = -1; // Input terminating value

// Read Inputs until sentinel encountered


cout << "Enter a positive integer or " << sentinel << " to exit: ";
while (cin >> numberIn && numberIn != sentinel) {
// Check input for positive integer
if (numberIn > 0) {
++count;
sum += numberIn;
max = max < numberIn ? numberIn : max;
min = min > numberIn ? numberIn : min;
}
else {
cout << "error: input must be positive! try again..." << endl;
}
cout << "Enter a positive integer or " << sentinel << " to exit: ";
}
// Print result
cout << endl << "Count is " << count << endl;
if (count > 0) {
cout << "Maximum is " << max << endl;
cout << "Minimum is " << min << endl;
cout << fixed << setprecision(2);
// print floating point to 2 decimal places (need <iomanip>)
cout << "Average is " << (double)sum / count << endl;
}
}

In this example, we use -1 as the sentinel value to indicate the end of inputs, which is a sequence
of positive integers. Instead of hard coding the value of -1, we use a variable called sentinel for
flexibility and ease-of-maintenance.
Department of Software Engineering, AASTU Page 22
Fundamentals of Programming I
(4) Nested Loops
You can nest loops of any kind one inside another to any depth. The following diagram
illustrates a nested for-loop, i.e., an inner for-loop within an outer for-loop.

int totalCount = 70
while(totalCount<600){
for(int i = 0; i < 10; i++){
totalCount += i;
if(totalCount>400)
break;
}
}

Exercise: Try out the following program, which prints a 6-by-8 checker box pattern
using nested loops, as follows:

########
########
########
########
########

Department of Software Engineering, AASTU Page 23


Fundamentals of Programming I

3.5 Interrupting Loop Flow (Exiting from loop)


(1) Break Statement
We have seen the use of the break statement in the switch statement. In loops, you can use the
break statement to exit the current loop you are in. Using break we can leave a loop even if the
condition for its end is not fulfilled (causes a jump out of these constructs, and hence terminates
them). It can be used to end an infinite loop, or to force it to end before its natural end.

Example (break): The following program lists the non-prime numbers between 2 and an
upper-bound.
// List non-prime from 1 to an upperbound (NonPrimeList.cpp).
#include <iostream>
#include <cmath>
using namespace std;

int main(){
int upperbound;
cout << "Enter the upperbound: ";
cin >> upperbound;
for (int number = 2; number <= upperbound; ++number)
{
// Not a prime, if there is a factor between 2 and sqrt(number)
int maxFactor = (int)sqrt(number);
for (int factor = 2; factor <= maxFactor; ++factor)
{
if (number % factor == 0) // Factor?
{
cout << number << " ";
break; // A factor found, no need to search for more factors
}
}
}
cout << endl;
return 0;
}

A break statement only applies to the “loop” or “switch” immediately enclosing it. It is an error
to use the break statement outside a loop or a switch statement.

Department of Software Engineering, AASTU Page 24


Fundamentals of Programming I
Let's rewrite the above program without using break statement. A while loop is used (which is
controlled by the Boolean flag) instead of for loop with break:

/*
* List primes from 1 to an upperbound (PrimeList.cpp).
*/
#include <iostream>
#include <cmath>
using namespace std;

int main()
{
int upperbound;
cout << "Enter the upperbound: ";
cin >> upperbound;

for (int number = 2; number <= upperbound; ++number)


{
// Not prime, if there is a factor between 2 and sqrt of number
int maxFactor = (int)sqrt(number);
bool isPrime = true;
int factor = 2;
while (isPrime && factor <= maxFactor)
{
if (number % factor == 0) { // Factor of number?
isPrime = false;
}
++factor;
}
if (isPrime) cout << number << " ";
}
cout << endl;
return 0;

Department of Software Engineering, AASTU Page 25


Fundamentals of Programming I
(2) The continue Statement
The continue statement causes the program to skip the rest of the loop in the current iteration as
if the end of the statement block had been reached, causing it to jump to the start of the following
iteration. Shortly it terminates the current iteration of a loop and instead jumps to the next
iteration. It is an error to use the continue statement outside a loop.

In while and do while loops, the next iteration commences from the loop condition; where in a
“for” loop, the next iteration commences from the loop’s third expression.

For example, we are going to skip the number 5 in our countdown:

// continue loop example 10, 9, 8, 7, 6, 4, 3, 2, 1, FIRE!


#include <iostream.h>
int main ()
{
for (int n=10; n>0; n--) {
if (n==5) continue;
cout << n << ", ";
}
cout << "FIRE!\n";
return 0;
}

Example (continue):

// Sum 1 to upperbound, exclude 11, 22, 33,...


int upperbound = 100;
int sum = 0;
for (int number = 1; number <= upperbound; ++number) {
if (number % 11 == 0)
continue; // Skip the rest of the loop body, continue to the next iteration
sum += number;
}
// It is better to re-write the loop as:
for (int number = 1; number <= upperbound; ++number) {
if (number % 11 != 0) sum += number;
}

Department of Software Engineering, AASTU Page 26


Fundamentals of Programming I
When the continue statement appears inside nested loops, it applies to the loop immediately
enclosing it, and not to the outer loops. For example, in the following set of nested loops, the
continue statement applies to the “for” loop, and not to the “while” loop.

while(true)
{
for(i=0; i<n; i++)
{
cin>>num;
if(num < 0)
continue; //causes a jump to : i++
sum += number;
}
}

Examples (break and continue): Study the following program.

/* A mystery series (Mystery.cpp) */


#include <iostream>
using namespace std;
int main()
{
int number = 1;
while (true)
{
++number;
if ((number % 3) == 0) continue;
if (number == 133) break;
if ((number % 2) == 0)
{
number += 3;
}
else {
number -= 3;
}
cout << number << " ";
}
cout << endl;
return 0;
}

Note: Break and continue are poor structures as they are hard to read and hard to follow. Use
them only if absolutely necessary. You can always write the same program without
using break and continue.

Department of Software Engineering, AASTU Page 27


Fundamentals of Programming I
(3) The goto statement
The goto statement allows making an absolute jump to another point in the program. You should
use this feature with caution since its execution causes an unconditional jump ignoring any type
of nesting limitations.

The destination point is identified by a label, which is then used as an argument for the goto
statement. It has the general form:

goto label;

where label is a valid identifier which marks the jump destination point of goto statement. The
label should be followed by a colon and appear before a statement within the same function as
the goto statement itself.
For example, here is our countdown loop using goto:

// goto loop example 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, FIRE!


#include <iostream.h>
int main ()
{
int n=10;
loop: //label
cout << n << ", ";
n--;
if (n>0)
goto loop;
cout << "FIRE!\n";
return 0;
}

Generally speaking, this instruction has no concrete use in structured or object oriented
programming aside from those that low-level programming fans may find for it.

Department of Software Engineering, AASTU Page 28


Fundamentals of Programming I

3.6 Terminating Program


There are a few ways that you can terminate your program, before reaching the end of the
programming statements.

(1) The exit function


You could invoke the function exit(int exitCode), in <cstdlib> (ported from C's "stdlib.h"), to
terminate the program and return the control to the Operating System. By convention, return
code of zero indicates normal termination; while a non-zero exitCode (-1) indicates abnormal
termination. For example,

void exit (int exitcode);

The exitcode is used by some operating systems and may be used by calling programs. By
convention, an exit code of 0 means that the program finished normally and any other value
means that some error or unexpected results happened.

(2) The abort function


The header <cstdlib> also provide a function called abort(), which can be used to terminate the
program abnormally.
if (errorCount > 10)
{
cout << "too many errors" << endl;
exit(-1); // Terminate the program
// OR abort();
}

(3) The "return" Statement:


You could also use a "return returnValue" statement in the main() function to terminate the
program and return control back to the Operating System. For example,

int main() {
...
if (errorCount > 10) {
cout << "too many errors" << endl;
return -1; // Terminate and return control to OS from
main()
}
...
}

Department of Software Engineering, AASTU Page 29


Fundamentals of Programming I

Exercises 1:
Print these patterns using nested loop (in a program called PrintPattern1x). Use a variable
called size for the size of the pattern and try out various sizes. You should use as few printing
statements as possible.

#*#*#*#* ######## ######## 1 1


#*#*#*#* ####### ####### 21 12
#*#*#*#* ###### ###### 321 123
#*#*#*#* ##### ##### 4321 1234
#*#*#*#* #### #### 54321 12345
#*#*#*#* ### ### 654321 123456
#*#*#*#* ## ## 7654321 1234567
#*#*#*#* # # 87654321 87654321

(a) (b) (c) (d) (e)

####### ####### ####### ####### #######


# # # # # # ## ##
# # # # # # # # # #
# # # # # # # #
# # # # # # ## ##
####### ####### ####### ####### #######

(f) (g) (h) (i) (j)

Department of Software Engineering, AASTU Page 30


Fundamentals of Programming I

3.7 Some Issues in Flow Control


Dangling else: The "dangling else" problem can be illustrated as follows:

if (i == 0)
if (j == 0)
cout << "i and j are zero" << endl;
else cout << "i is not zero" << endl; // intend for the outer-if

The else clause in the above codes is syntactically applicable to both the outer-if and the inner-if.
The C++ compiler always associate the else clause with the innermost if (i.e., the nearest if).
Dangling else can be resolved by applying explicit parentheses. The above codes are logically
incorrect and require explicit parentheses as shown below.

if ( i == 0)
{
if (j == 0) cout << "i and j are zero" << endl;
}
else
{
cout << "i is not zero" << endl; // non-ambiguous for outer-if
}

Endless Loop: The following constructs:

while (true) for (initialization; condition;)


{ {
...... ......
} }

It is commonly used. It seems to be an endless loop (or infinite loop), but it is usually terminated
via a break or return statement inside the loop body. This kind of code is hard to read - avoid if
possible by re-writing the condition

Department of Software Engineering, AASTU Page 31


Fundamentals of Programming I

3.8 Formatting Input/Output using I/O Manipulators


The <iomanip> header provides so-called I/O manipulators for formatting input and output:

 setw(int field-widht): set the field width for the next IO operation. setw() is non-sticky and
must be issued prior to each IO operation. The field width is reset to the default after each
operation (with just enough width to accommodate the field).

 setfill(char fill-char): set the filled character for padding to the field width.

 left|right|internal: set the alignment

 fixed/scientific (for floating-point numbers): use fixed-point notation (e.g, 12.34) or


scientific notation (e.g., 1.23e+006).

 setprecision(int numDecimalDigits) (for floating-point numbers): specify the number of


digits after the decimal point.

 boolalpha/noboolalpha (for bool): display bool values as alphabetic string (true/false) or 1/0

Example 1: Output Formatting

/* Test Formatting Output (TestFormattedOutput.cpp) */


#include <iostream>
#include <iomanip> // Needed to do formatted I/O
using namespace std;
int main() {
// Floating point numbers
double pi = 3.14159265;
cout << fixed << setprecision(4); // fixed format with 4 decimal places
cout << pi << endl;
cout << "|" << setw(8) << pi << "|" << setw(10) << pi << "|" << endl;
// setw() is not sticky, only apply to the next operation.
cout << setfill('-');
cout << "|" << setw(8) << pi << "|" << setw(10) << pi << "|" << endl;
cout << scientific; // in scientific format with exponent
cout << pi << endl;
// booleans
bool done = false;
cout << done << endl; // print 0 (for false) or 1 (for true)
cout << boolalpha; // print true or false
cout << done << endl;
return 0;
}

Department of Software Engineering, AASTU Page 32


Fundamentals of Programming I
Example 2: Output Formatting

/* Test Formatting Input (TestFormattedInput.cpp) */


#include <iostream>
#include <iomanip>
#include <string>
using namespace std;

int main() {
string areaCode, phoneCode;
string inStr;

cout << "Enter your phone number in this format (xxx)xxx-xxxx : ";
cin.ignore(); // skip '('
cin >> setw(3) >> areaCode;
cin.ignore(); // skip ')'
cin >> setw(3) >> phoneCode;
cin.ignore(); // skip '-'
cin >> setw(4) >> inStr;
phoneCode += inStr;

cout << "Phone number is (" << areaCode << ")"


<< phoneCode.substr(0, 3) << "-"
<< phoneCode.substr(3, 4) << endl;
return 0;
}

************* End *************

Department of Software Engineering, AASTU Page 33

You might also like