2.条件分岐と反復
Cプログラムの基本構造は、「順次構造」、「選択構造」、「反復構造」の3つからなると考えられます。基本的にはプログラムは先頭行から順に実行されていきます(順次構造)が、実際にはその流れを条件によって分岐させたり(選択構造)、同じ箇所を繰り返し実行させたりすること(反復構造)を頻繁に行います。この条件分岐と反復を、目的に応じて使いこなすことこそがプログラミングの要である、といっても過言ではありません。
2.1 選択構造
if文(if~else文)とswitch文があります。
2.1.1 if文
下の例は、キーボードから入力した整数の値が10より大きいか小さいかを、if文を使って判断して、その結果を表示するものです。
<例2−1>
#define BORDER 10 /* BORDERを10と定義 */
#include <stdio.h>
int main(void) {
int
num;
/*
キーボードからの整数値をnumに格納 */
printf("Input
a number: ");
scanf("%d",
&num);
if
(num > BORDER) { /* numがBORDERより大きかったら... */
printf("%d
is bigger than %d.\n", num, BORDER);
}
else if (num < BORDER) { /*
numがBORDERより小さかったら... */
printf("%d
is smaller than %d\n", num, BORDER);
}
else { /*
それ以外だったら(numとBORDERが等しかったら)... */
printf("%d
is equal to %d\n", num, BORDER);
}
return
0;
}
[解説] #define文
[解説] scanf関数
ここではifとelseを使って多項の条件分岐をさせていることを理解してください。
【課題2−1】(プログラムを提出)
以下のプログラムは、キーボードから3つの実数値を入力し、単にその値を表示するものである。これを、「はじめの2つの数の和が、3つめの数より大きいか小さいか等しいかを判断し、その結果を出力するプログラム」に書き換える。
#include <stdio.h>
int main(void) {
double
x, y, z;
/*
キーボードから3つの実数値をx, y, zに入力 */
printf("Input
three real numbers (separate by space):");
scanf("%lf
%lf %lf", &x, &y, &z);
/*
x, y, zの値を表示 */
printf("%4.3f
%4.3f %4.3f\n", x, y, z);
return
0;
}
[解説] printf関数のオプション指定
《プログラム例》
2.1.2 switch文
多項分岐をさせる場合、switch文を使った方がプログラムがすっきりすることがあります。
<例2−2>
#include <stdio.h>
int main(void) {
int
num;
/*
キーボードから1から5の値を入力 */
printf("Input
a number (1-5): ");
scanf("%d",
&num);
/*
入力された値に従って分岐 */
switch
(num) {
case
1: printf("one\n");
break;
case
2:
case
3:
printf("two
or three\n");
break;
case
4:
printf("four
or ");
case
5:
printf("five\n");
break;
default:
printf("out
of range\n");
}
return
0;
}
上の例は入力した整数の値に応じて文字列を表示するものです。switch, case, break, defaultといった命令がどのような意味を持つかを考えてもらうために、あえて妙なプログラムにしてあります。実行してその動作を確かめてください。
【課題2−2】(プログラムを提出)
以下のプログラムは、入力した2つの整数値と演算子(+, -, *, /, %)に応じて演算結果を表示するものである(入力は、数<space>演算子<space>数、という形式)。これをswitch文をつかって書き換える。
#include <stdio.h>
int main(void) {
int
n, m, result;
char
op; /*
演算子を表す文字を格納する変数 */
/*
2つの整数値と演算子を入力 */
printf("Input
two numbers and an operator (e.g., 10 * 15): ");
scanf("%d
%c %d", &n, &op, &m);
/*
入力された演算子に従って分岐して処理 */
if
(op == '+') {
result
= n + m;
}
else if (op == '-') {
result
= n - m;
}
else if (op == '*') {
result
= n * m;
}
else if (op == '/') {
result
= n / m;
}
else if (op == '%') {
result
= n % m;
}
else {
printf("Unknown
operator \"%c\".\n", op);
return
1;
}
printf("Answer:
%d\n", result); /*
答えの表示 */
return
0;
}
[解説] エスケープ文字
《プログラム例》
2.2 反復構造
for文、while文、do~while文があります。どの文も他の文で書き換えることができます。どれを使うかはプログラマの好みによる部分もあります。
2.2.1 for文
指定された回数の反復処理を行う際によく用いられます。
<例2−3>
int main(void) {
int
i, sum=0;
/*
forループ */
/*
iを1で初期化、ループの最後でiに1を足し、iが10になるまで繰り返す */
for
(i = 1; i <= 10; i++) {
sum
+= i;
}
return
0;
}
[解説] +=や-=などの代入演算子
上の例は1から10までの数の和を求めるものです。
2.2.2 while文
条件式を前判定して反復します。特定の目的まで処理を繰り返すのによく用いられます。
<例2−4>
#include <stdio.h>
int main(void) {
int
n=0;
/*
whileループ */
/*
nに999が入力されるまでループを繰り返す */
while
(n != 999) {
printf("Input
a number (999 to abort): ");
scanf("%d",
&n);
}
return
0;
}
[解説] 無限ループ
この例は、999が入力されるまで繰り返し入力を要求するものです。
2.2.3 do~while文
条件を後判定して反復します。「条件はどうであれ1回は必ず実行する」という場合に便利です。
<例2−5>
#include <stdio.h>
int main(void) {
int
n=0, sum=0, cnt=0;
/*
do-whileループ */
do
{
printf("Input
a number:");
scanf("%d",
&n);
printf("Sum
of %d values: %d\n", ++cnt, sum+=n);
}
while (sum <= 100); /* sumが100を超えたら繰り返しをやめる */
}
[解説] ++と--
この例は、入力した整数の和が100を超えるまで繰り返し入力を要求するものです。始めにどんな値が入力されようと、とにかくsumに加えて結果を表示します。
【課題2−3】(プログラムと実行結果を提出)
これまでの例や課題を参考にして、以下のようなプログラムを作る。
「10人の学生について、100点満点のテストの合否判定(60点以上が合格)を行う。個々の点数を一つずつ入力していき、合格者数、不合格者数、最高点、最低点、平均点を計算し、出力する。」
【余力がある人は...】
「得点によって成績をA,B,C,Dにわけ、それぞれの人数を集計する」、
「10人だけでなく、不特定多数の学生のデータを集計できるようにする」、
「負の数や100より大きい数が入力された場合には入力ミスとみなし、その場合は再入力を促す」
といった機能をつけてみる。
[解説] 最大値や最小値の求め方
《プログラム例》