コンピュータ基礎および演習II

例題

- 配列を用いた大量データの扱い

今まで学んだ知識では、 変数を宣言したぶんのデータの個数しか扱うことができませんでした。 例えば変数を1000個宣言し使うのは非現実的です。 Java で大量のデータを扱うための基本的な機能が「配列 (Array) 」です。 配列は同じ種類のデータの集まりに一つの名前をつけ、 ひとまとめにして扱うものです。 そして、一つ一つのデータは番号で指定します。

配列についての文法的な説明は 「エッセンシャルJava」の pp.50〜65 を参照してください。

- 例題: 与えられた数の合計を求める

プログラムの先頭で int 型の配列を用意し、 複数の整数を代入しておきます。 その合計を求めるプログラムを考えてみます。 さらにこのプログラムでは、合計を表示した後、 元の数を改めて表示することにします。

ファイル名は SumAndList.java とします。

2 つの for 文があります。 1 つめの for 文で a の各要素の合計を求め、 2 つめの for 文で各要素の値を表示しています。 for 文の 2 番目の式の a.length は 配列 a の要素数を求める書き方です。

いずれの for 文も、a[0], a[1], a[2], ..., a[4] の順に配列 a の要素を処理しています。 この for 文の中身は i を 0 から 1 ずつ増やしていき、 i が 4 になるまで合計 5 回繰り返されます。

for 文の形は 2 つとも同じで、次のようになっています。

for (i = 0; i < a.length; i++)
    処理

この形が配列の要素を 0 から順に処理する際の標準的な書き方なので、 身につけておくべきです。

ところで、配列の宣言、初期化の書き方には何種類かあります。 このプログラムの 5,6 行目を 1 つにまとめて、

int[] a = new int[5];

と書くこともできます。 また、宣言と初期化を同時に行い、 5 〜 11 行目をまとめて、

int[] a = new int[]{3, 5, 6, 1, 9};

と書くこともできます。

int[] a;int a[]; は同じ意味です。 前者の書き方がお勧めです。

配列は、宣言された要素の数を越えて使うことはできません。 また、要素の番号に負の数を使うことはできません。 a[i]i のように、 配列要素の番号を示す整数を「添字 (そえじ) 」と呼びます。 添字は 0 以上、要素数未満である必要があります。

範囲外の配列の要素にアクセスしようとすると、 Java では例外 (Exception) と呼ばれる一種のエラーが発生し、 プログラムが強制的に終了してしまいます。 このようなことを防ぐために、 配列にアクセスする際には、 添字がその配列の範囲内にあるかどうかについて常に気を配る必要があります。

- 例題: 最小の要素を探す

第 2 回目の例題で、 3 つの値の最大値を求めるプログラム を取り上げました。 この例題の 3 番目のプログラムの考え方をもとに、 任意の大きさの配列から最小の値を探し出すプログラムを考えてみましょう。

ファイル名は SearchMinimum.java とします。

for 文で、要素を一つ一つ比較し、 変数 minValue に、 それまでに見つかった最小の値を入れておくようにします。 また、最小値の入っている要素の番号を minIndex に入れておきます。 全ての要素を検査し終わり、for 文を抜けると、 変数 minValue に、最小の値が入っていることになります。

- 例題: 整列を行う

整列 (Sorting) とは、 データの集まりを値の大きさの順に並び替えることを言います。 小さい順に並べることを昇順 (Ascending order) 、 逆に、大きい順に並べることを降順 (Descending order) といいます。

整列は、コンピュータを用いてよく行われる一般的な処理で、 様々なアルゴリズム (Algorithm, プログラムの書き方の手法) が考案されてきましたが、 最も簡単な単純選択法 (Selection sort, 選択ソート) と呼ばれる方法を プログラムとして書いてみましょう。

ファイル名は SelectionSort.java とします。

値を昇順に並べる選択ソートの働きは、 配列から最小の値を探し、それを配列の先頭に移動するという動作を繰り返します。 具体的には次のような手順です。

  1. すべての要素から最小の値を探し、それを配列の先頭に移動する。
  2. 先ほどの最小の値を除いた残りの要素から最小の値を探し、それを配列の 2 番目に移動する。
  3. 同様に、さらに残りの要素から最小の値を探し、配列の先頭部分に移動する。これを繰り返す。

配列の最後まで最小の値を移動し終わったところで、 その配列は小さい順に並んでいることになります。 これを、プログラムとして書くと次のようになるでしょう。

  1. まず a[0] から a[n] までの最小の値を探し、それを a[0] と交換する。
  2. 次に a[1] から a[n] までの最小の値を探し、それを a[1] と交換する。
  3. 同様に a[2], a[3], ... a[n-1] について繰り返す。

移動ではなく「交換」としているのは、 配列は先頭や途中に要素を付け足したり、削除することができないからです。 まだ並び替えられていない残りの要素は、 交換によって順番が変化しても構いません。

外側の for 文では、変数 i を 0 から要素数-1 まで増やし、繰り返します。 a[i] から a[要素数-1] のうち、 最小の値を探し、最小の値を変数 minValue に その要素の番号を minIndex に入れておきます。 そして、 a[i]と交換します。

ある 2 つの変数の値を交換する場合、単純に代入しただけでは、 元の変数の値が上書きされてしまいます。そこで、変数 temp を使い、いったん a[i] の値を保存しておき、 a[i]a[minIndex] の値を代入しています。 そして、 a[minIndex]temp に保存しておいた 元の a[i] を代入しています。

最後に、整列済みの a の要素を順に表示しています。

- コマンドライン引数

コマンドライン引数 (ひきすう) (Command Line Argument) とは、 Java のプログラムを実行を開始するときに、 指定した文字列をプログラムに渡すことができるものです。 これにより、実行時にプログラムの動きを変えたり、 値をプログラムに渡すことができます。

例えば、プログラムが次のコマンドで起動されたとします。

java AClass filename condition

このコマンドには通常の Java プログラムの実行コマンドに加えて、 filename と condition の 2 つの引数があります。 UNIX のコマンドは一般にスペースで引数を区切る約束になっています。

Java のプログラムの始めには public static void main(String[] args) という記述があり、この中に

String[] args 

という配列の宣言のような記述があることに気がついたでしょう。 コマンドライン引数は文字列型配列 args の要素として取り出すことができます。

args の要素は文字列です。 この例では、配列要素 args[0] には "filename" が、 args[1] には "condition" が入ります。 このように「n 番目の引数」は args[n] として取り出すことができます。