3.2. Control of flow3.2.1. The if statementThe if(expression) statement if(expression) statement1 else statement2 In the first form, if (and only if) the expression is
non-zero, the statement is executed. If the
expression is zero, the statement is ignored.
Remember that the statement can be compound; that is the way to
put several statements under the control of a single The second form is like the first except that if the statement shown as statement1 is selected then statement2 will not be, and vice versa. Either form is considered to be a single statement in the syntax of C, so the following is completely legal.
if(expression)
if(expression) statement
The first if(expression) statement and is therefore itself properly formed. The argument can be extended as far as you like, but it's a bad habit to get into. It is better style to make the statement compound even if it isn't necessary. That makes it a lot easier to add extra statements if they are needed and generally improves readability. The form involving
if(expression)
if(expression)
statement
else
statement
As Chapter 1 has said already, this is now ambiguous. It is
not clear, except as indicated by the indentation, which of the
That is not the way that C views it. The rule is that an
To prevent any unwanted association between an
if(expression){
if(expression)
statement
}else
statement
Putting in all the compound statement brackets, it becomes this:
if(expression){
if(expression){
statement
}
}else{
statement
}
If you happen not to like the placing of the brackets, it is up to you to put them where you think they look better; just be consistent about it. You probably need to know that this a subject on which feelings run deep. 3.2.2. The while and do statementsThe
while(expression)
statement
The statement is only executed if the expression
is non-zero. After every execution of the statement, the
expression is evaluated again and the process repeats if it is
non-zero. What could be plainer than that? The only point to watch out for
is that the statement may never be executed, and that if
nothing in the statement affects the value of the expression
then the It is occasionally desirable to guarantee at least one execution of the statement following the while, so an alternative form exists known as the do statement. It looks like this:
do
statement
while(expression);
and you should pay close attention to that semicolon—it is not
optional! The effect is that the statement part is executed before the
controlling expression is evaluated, so this guarantees at least one trip
around the loop. It was an unfortunate decision to use the keyword
If you feel the urge to use a 3.2.2.1. Handy hintsA very common trick in C programs is to use the result of
an assignment to control
#include <stdio.h>
#include <stdlib.h>
main(){
int input_c;
/* The Classic Bit */
while( (input_c = getchar()) != EOF){
printf("%c was read\n", input_c);
}
exit(EXIT_SUCCESS);
}Example 3.2The clever bit is the expression assigning to Note that Both the 3.2.3. The for statementA very common feature in programs is loops that are controlled by variables used as a counter. The counter doesn't always have to count consecutive values, but the usual arrangement is for it to be initialized outside the loop, checked every time around the loop to see when to finish and updated each time around the loop. There are three important places, then, where the loop control is concentrated: initialize, check and update. This example shows them.
#include <stdio.h>
#include <stdlib.h>
main(){
int i;
/* initialise */
i = 0;
/* check */
while(i <= 10){
printf("%d\n", i);
/* update */
i++;
}
exit(EXIT_SUCCESS);
}Example 3.3As you will have noticed, the initialization and check parts of the loop
are close together and their location is obvious because of the presence
of the for (initialize; check; update) statement The initialize part is an expression; nearly always an assignment expression which is used to initialize the control variable. After the initialization, the check expression is evaluated: if it is non-zero, the statement is executed, followed by evaluation of the update expression which generally increments the control variable, then the sequence restarts at the check. The loop terminates as soon as the check evaluates to zero. There are two important things to realize about that last description: one, that each of the three parts of the for statement between the parentheses are just expressions; two, that the description has carefully explained what they are intended to be used for without proscribing alternative uses—that was done deliberately. You can use the expressions to do whatever you like, but at the expense of readability if they aren't used for their intended purpose. Here is a program that does the same thing twice, the first time using a
#include <stdio.h>
#include <stdlib.h>
main(){
int i;
i = 0;
while(i <= 10){
printf("%d\n", i);
i++;
}
/* the same done using ``for'' */
for(i = 0; i <= 10; i++){
printf("%d\n", i);
}
exit(EXIT_SUCCESS);
}Example 3.4There isn't any difference betweeen the two, except that in this case
the Any of the initialize, check and update expressions in the for statement can be omitted, although the semicolons must stay. This can happen if the counter is already initialized, or gets updated in the body of the loop. If the check expression is omitted, it is assumed to result in a ‘true’ value and the loop never terminates. A common way of writing never-ending loops is either for(;;) or while(1) and both can be seen in existing programs. 3.2.4. A brief pauseThe control of flow statements that we've just seen are quite adequate
to write programs of any degree of complexity. They lie at the core
of C and even a quick reading of everyday C programs will
illustrate their importance, both in the provision of essential
functionality and in the structure that they emphasize. The remaining
statements are used to give programmers finer control or to make it easier
to deal with exceptional conditions. Only the 3.2.5. The switch statementThis is not an essential part of C. You could do without it, but the language would have become significantly less expressive and pleasant to use. It is used to select one of a number of alternative actions depending on
the value of an expression, and nearly always makes use of another of the
lesser statements: the
switch (expression){
case const1: statements
case const2: statements
default: statements
}
The expression is evaluated and its value is compared with
all of the const1 etc. expressions, which must all evaluate
to different constant values (strictly they are integral constant
expressions, see Chapter 6 and below). If any of them
has the same value as the expression then the statement
following the One curious feature is that the cases are not exclusive, as this example shows.
#include <stdio.h>
#include <stdlib.h>
main(){
int i;
for(i = 0; i <= 10; i++){
switch(i){
case 1:
case 2:
printf("1 or 2\n");
case 7:
printf("7\n");
default:
printf("default\n");
}
}
exit(EXIT_SUCCESS);
}Example 3.5The loop cycles with The labels can occur in any order, but no two values may be the same and
you are allowed either one or no The expression controlling the 3.2.5.1. The major restrictionThe biggest problem with the
#include <stdio.h>
#include <stdlib.h>
main(){
int i;
for(i = 0; i <= 10; i++){
switch(i){
case 1:
case 2:
printf("1 or 2\n");
break;
case 7:
printf("7\n");
break;
default:
printf("default\n");
}
}
exit(EXIT_SUCCESS);
}Example 3.6The 3.2.5.2. Integral Constant ExpressionAlthough Chapter 6 deals with constant expressions, it is
worth looking briefly at what an integral constant expression is, since
that is what must follow the Much what you would expect, really. 3.2.6. The break statementThis is a simple statement. It only makes sense if it occurs in the body
of a The use of the
#include <stdio.h>
#include <stdlib.h>
main(){
int i;
for(i = 0; i < 10000; i++){
if(getchar() == 's')
break;
printf("%d\n", i);
}
exit(EXIT_SUCCESS);
}Example 3.7It reads a single character from the program's input before printing the
next in a sequence of numbers. If an ‘ If you want to exit from more than one level of loop, the
3.2.7. The continue statementThis statement has only a limited number of uses. The rules for its use
are the same as for
#include <stdio.h>
#include <stdlib.h>
main(){
int i;
for(i = -10; i < 10; i++){
if(i == 0)
continue;
printf("%f\n", 15.0/i);
/*
* Lots of other statements .....
*/
}
exit(EXIT_SUCCESS);
}Example 3.7You could take a puritanical stance and argue that, instead of a
conditional Of course the Do remember that There is an important difference between loops written with
3.2.8. goto and labelsEverybody knows that the What's especially annoying is that there are times when it is the most
appropriate thing to use in the circumstances! In C, it is used to
escape from multiple nested loops, or to go to an error handling exit at
the end of a function. You will need a label when you use a
goto L1; /* whatever you like here */ L1: /* anything else */ A label is an identifier followed by a colon. Labels have their own
‘name space’ so they can't clash with the names of variables or
functions. The name space only exists for the function containing the
label, so label names can be re-used in different functions. The label can
be used before it is declared, too, simply by mentioning it in a
Labels must be part of a full statement, even if it's an empty one. This usually only matters when you're trying to put a label at the end of a compound statement—like this. label_at_end: ; /* empty statement */ } The It's hard to give rigid rules about the use of SummaryNow we've seen all of the control of flow statements and examples of their use. Some should be used whenever possible, some are not for use line by line but for special purposes where their particular job is called for. It is possible to write elegant and beautiful programs in C if you are prepared to take the extra bit of care necessary; the specialized control of flow statements give you the chance to add the extra polish that some other languages lack. All that remains to be done to complete the picture of flow of control in C is to finish off the logical operators. |
The C BookThis book is published as a matter of historical interest. Please read the copyright and disclaimer information. GBdirect Ltd provides up-to-date training and consultancy in C, Embedded C, C++ and a wide range of other subjects based on open standards if you happen to be interested. |
|
West Yorkshire Office
GBdirect Ltd
Training: 0800 651 0338 Please call between 0900 and 1700 (UK time) on Monday to Friday South East Regional Office
GBdirect Ltd
Training: 0800 651 0338 Please call between 0900 and 1700 (UK time) on Monday to Friday Please note: |