第4日目:繰り返し処理
繰り返し処理の基礎
繰り返し処理とは
第3日目では、条件に応じて処理を分岐させる「分岐処理」を学びました。プログラムの処理には「順次処理」「分岐処理」に加えて、もう一つ重要な処理があります。それが繰り返し処理です。
繰り返し処理とは、ある条件が成立する間、同じ処理を何度も繰り返す処理のことです。例えば、「1から5までの数値を順に表示する」「指定した回数だけ同じ処理を行う」といった場合に使用します。
Javaでは、繰り返し処理を実現するための命令として、for文・while文・do~while文の3つが用意されています。
for文
サンプルプログラム
まずは、以下のサンプルを実行してみてください。
package day4;
public class Sample401 {
public static void main(String[] args) {
for(int i = 1;i <= 5;i++){
System.out.print(i+" ");
}
System.out.println();
}
}
このプログラムでは、変数iを1から始め、iが5以下である間、iを1ずつ増やしながら処理を繰り返しています。その結果、1から5までの数値が順番に表示されます。このような処理をforループと言います。(図4-1)
図4-1:forループの仕組み
for文の書式
処理
}
for文の()内には、セミコロン(;)で区切られた3つの要素を記述します。
- 初期化処理:ループが始まる前に1回だけ実行される処理です。ループに使う変数を初期化します。(例:int i = 1)
- 条件式:この条件がtrueである間、ループを繰り返します。(例:i <= 5)
- 増分処理:ループの1回ごとに実行される処理です。変数の値を変化させます。(例:i++)
インクリメント・デクリメント
for文の増分処理でよく使われるi++は、変数iの値を1増やすという意味です。このように変数の値を1増加させることをインクリメント、1減少させることをデクリメントと言います。Javaで使用できるインクリメント・デクリメントの演算子は以下の表4-1のとおりです。
| 演算子 | 呼び名 | 意味 | 該当する演算 |
|---|---|---|---|
| i++ | インクリメント(後置) | 変数の値を1増加させる | i=i+1; i+=1; |
| ++i | インクリメント(前置) | 変数の値を1増加させる | |
| i-- | デクリメント(後置) | 変数の値を1減少させる | i=i-1; i-=1; |
| --i | デクリメント(前置) | 変数の値を1減少させる |
インクリメントには前置(++i)と後置(i++)の2種類があります。前置は演算の終了後に左辺の値に代入されるのに対し、後置は代入の後に演算を行います。現代のコンピュータではリソースの差が無視できる程度であるため、ほとんどの場合は使い分けられていません。
二重ループ
サンプルプログラム
for文の中にさらにfor文を記述することができます。このような構造を二重ループと言います。以下のサンプルを実行してみましょう。
package day4;
public class Sample402 {
public static void main(String[] args) {
for(int i = 1;i <= 2;i++){
for(int j = 1; j <= 3 ; j++){
int k = i + j;
System.out.print(i+"+" + j + "=" + k +" ");
}
System.out.println();
}
}
}
2+1=3 2+2=4 2+3=5
外側のループ(変数i)が1回実行されるごとに、内側のループ(変数j)が最初から最後まで実行されます。外側のiが1のとき、内側のjが1〜3まで繰り返されて1行目が出力され、iが2のとき、同様にjが1〜3まで繰り返されて2行目が出力されます。
二重ループは3重・4重と重ねることも可能ですが、深くなるほどプログラムが複雑になるため、注意が必要です。
while文
サンプルプログラム
for文と同様に繰り返し処理を実現する方法として、while文があります。以下のサンプルを実行してみましょう。
package day4;
public class Sample403 {
public static void main(String[] args) {
int i = 0;
while(i <= 5){
System.out.print(i+" ");
i++;
}
System.out.println();
}
}
このプログラムでは、iが5以下である間、iの値を表示してからiを1増やす処理を繰り返しています。while文は、条件式の判定が最初に行われるため、最初から条件が成立しない場合は一度も処理が実行されません。(図4-2)
図4-2:whileループの仕組み
while文の書式
処理
}
()の中の条件式がtrueである間、{ }内の処理を繰り返します。for文と異なり、初期化処理や増分処理はwhile文の外に記述します。
do~while文
サンプルプログラム
繰り返し処理のもう一つの方法として、do~while文があります。以下のサンプルを実行してみましょう。
package day4;
public class Sample404 {
public static void main(String[] args) {
int i = 0;
do{
System.out.print(i+" ");
i++;
}while(i <= 5);
System.out.println();
}
}
実行結果はwhile文と同じですが、do~while文は条件式の判定が後ろについているだけで、while文とまったく同じ働きをします。(図4-3)
図4-3:do~whileループの仕組み
do~while文の書式
処理
}while(条件式);
while文と異なり、do~while文は最初にdoの{ }内の処理を実行し、その後に条件式を判定します。そのため、条件を満たしていなくても最低限1回は処理が実行されるという特徴があります。また、末尾のwhile(条件式)の後にはセミコロン(;)が必要な点に注意しましょう。
whileとdo~whileの違い
サンプルプログラム
whileとdo~whileの動作の違いを確認するサンプルを見てみましょう。
package day4;
public class Sample405 {
public static void main(String[] args) {
int i,num;
num = 1;
System.out.print("whileで実行:");
i = 1;
while(i < num){
System.out.print("*");
i++;
}
System.out.println();
System.out.print("do~whileで実行:");
i = 1;
do{
System.out.print("*");
i++;
}while(i < num);
}
}
do~whileで実行:*
numに1が入っているため、「i < num」(1 < 1)は最初から成立しません。while文の場合、条件が成立しないため一度も「*」が表示されません。一方、do~while文の場合は、最初に処理を実行してから条件を判定するため、条件が成立しなくても1回だけ「*」が表示されます。
無限ループ
サンプルプログラム
最後に、無限ループとそこから脱出するためのbreakについて学びましょう。以下のサンプルを実行してみてください。
package day4;
public class Sample406 {
public static void main(String[] args) {
System.out.println("6が出たら終了");
while(true){
int dice = (int)(Math.random()*6)+1;
System.out.println(dice);
if(dice == 6){
break;
}
}
System.out.println("終了");
}
}
2
2
3
6
終了
乱数を使っているため、実行結果は毎回異なります。さいころの目が6になるまで繰り返し、6が出た時点でループを終了します。
無限ループとbreak
while(true)とすると、条件式が常にtrueであるため、処理が無限に繰り返されます。これを無限ループと言います。
無限ループから抜け出すには、breakを使います。breakが実行されると、そのループから即座に抜け出すことができます。このサンプルでは、さいころの目が6になったとき(dice == 6)にbreakが実行され、ループを終了しています。
なお、breakはswitch文(第3日目)でも使用しましたが、for文・while文・do~while文のループからも同様に抜け出すことができます。