コレクション

コレクションとは

すでに学んだとおり、大量のデータを扱うときには、配列を使いました。しかし、配列には一つ欠点があります。それは、あらかじめ、格納するデータの数が決まっていることです。しかし、場合によっては、あらかじめどれだけのデータを格納するかわからない時があります。その時便利なのが、Collection(コレクション)です。

サンプルプログラム

では、コレクションがどのようなものかを説明する前に、まずはサンプルプログラムを見てみましょう。

Student.java
package exday5;

public class Student {
	//	名前
	private String name;
	//	学年
	private int grade;
	//	番号
	private int number;
	//	コンストラクタ
	public Student(String name,int grade,int number){
		this.name = name;
		this.grade = grade;
		this.number = number;
	}
	//	名前の取得
	public String getName(){
		return name;
	}
	//	学年の取得
	public int getGrade(){
		return grade;
	}
	//	番号の取得
	public int getNumber(){
		return number;
	}

}

SampleEx501.java
package exday5;

import java.util.*;

public class SampleEx501 {

	public static void main(String[] args) {
		ArrayList al = new ArrayList();
		al.add(new Student("安藤一郎",1,1));
		al.add(new Student("伊藤花子",1,2));
		al.add(new Student("太田たかし",2,3));
		al.add(new Student("加藤紀子",2,4));
		al.add(new Student("木田直美",3,5));
		//	3番目を削除
		al.remove(3);
		for(int i = 0; i < al.size() ; i++){
			Student s = (Student)al.get(i);	//	i番目のオブジェクトを取得
			System.out.println("番号:" + s.getNumber() + " 名前: " + s.getName() + " 学年" + s.getGrade());
		}

	}

}
実行結果
番号:1 名前: 安藤一郎 学年1
番号:2 名前: 伊藤花子 学年1
番号:3 名前: 太田たかし 学年2
番号:5 名前: 木田直美 学年3

最初、alに5人分のデータを登録します。続いて、3番目の要素を削除し、最後には残っている成分を表示してます。

ArrayListクラス

手始めに、プログラムで出てくるArrayListクラスを見てみましょう。ArrayListクラスは、java.utilというパッケージに含まれています。そのため、通所、そのままでは使用できず、3行目で行われているように、まずこのパッケージを読み込むことから始めています。

java.util.パッケージの読み込み(インポート)
import java.util.*;

なお、ArrayListクラスには、以下のような主要なメソッドが存在します。*マークは、「全て」という意味があります。つまり、これにより、このプログラムでは、java.util パッケージをインポートして使用する、ということを意味するのです。

表5-1.ArrayListクラスの主要メソッド
メソッド 働き
add() コレクションに要素を追加します。
add() コレクションに要素を追加します。
size() コレクションに格納されている要素数を取得します。
remove() 指定された番号の要素をコレクションから削除します。
isEmpty() リストに要素がない場合に true を返します。

データの追加

データの追加は、add()メソッドで行います。SampleEx501.javaの9行目から13行目が、それにあたります。データは、追加した順番に、0,1,2,…と、番号が割り振られます。(図5-1.参照)

図5-1.ArrayListにデータを追加

ArrayListにデータを追加

データの削除

データの削除は、remove()メソッドで行います。SampleEx501.javaの15行目が、それにあたります。その際、引数として与えた番号のデータがなくなりますが、それ以降の番号は、繰り上がっていきます。

図5-2.ArrayListからデータを削除

ArrayListからデータを削除

ジェネリクスによる型の指定

ArrayListの問題点

SampleEx501.javaは、問題なくできますが、以下のような警告が発せられると思います。

SampleEx501.javaで発する警告
説明 リソース パス ロケーション 型 ArrayList は raw 型です。総称型 ArrayList<E> への参照は、パラメーター化する必要があります SampleEx501.java /1week/src/exday5 行 8 Java 問題

いったいなぜ、子のような警告が出てくるのでしょうか?実は、通常、ArrayListにデータを追加する際には、すべてのクラスのベースクラスとなる、Objectクラスのデータとして格納されるのです。

つまり、この状態だと、ArrayListにどんなデータでも追加できてしまうことになります。String型のデータを入れるはずのところに、違うクラスのインスタンスを格納することも可能となり、問題が発生する可能性があります。

こういうとき、ジェネリクスと呼ばれるものを用いれば、ArrayListの型を限定してしまうことができるのです。

サンプルプログラム

では実際に、ジェネリクスを用いてSampleEx501.javaを書き換えてみましょう。

SampleEx502.java
package exday5;

import java.util.*;

public class SampleEx502 {

	public static void main(String[] args) {
		ArrayList<Student> al = new ArrayLis<Student>();
		al.add(new Student("安藤一郎",1,1));
		al.add(new Student("伊藤花子",1,2));
		al.add(new Student("太田たかし",2,3));
		al.add(new Student("加藤紀子",2,4));
		al.add(new Student("木田直美",3,5));
		//	3番目を削除
		al.remove(3);
		//	特殊for文による結果の出力
		for(Student s : al){
			System.out.println("番号:" + s.getNumber() + " 名前: " + s.getName() + " 学年" + s.getGrade());
		}

	}

}

実行結果は同じなので省略します。しかし、このプログラムからは、警告が消えました。いったいなぜでしょうか?

ジェネリクスによる型の限定

その原因は、8行目にあります。8行目のArrayListの生成が、以下のように変わっています。

ジェネリクスを用いたArrayListの生成
ArrayList<Student> al = new ArrayLis<Student>();

ArrayListクラスの後に、<Student>と書いてあります。これは、<と>で囲まれた部分のクラスに、データの格納を限定するということを意味します。このように、<と>で型を指定する仕組みのことを、ジェネリクスと言います。

この型を用いると、ArrayListに追加できるデータの型を限定できるので、安心してArrayListを使うことが可能です。

特殊for文

また、このプログラムの17行目から19行目で用いられているfor文は、SampleEx501.javaとはかなり違います。これはいったい何でしょうか?このようなfor文は、特殊for文と呼ばれ、以下のような書式で記述します。

特殊for文の記述
for((クラス名) 変数 : コレクション)){

}

このようにすると、コレクションに入っている値が、変数に一つづつ代入され、コレクション内のすべてのデータを出しつくすと、ループが終了するようになっています。(図5-3.参照)ArrayListに限らず、コレクションと特殊for文は切っても切り離せない関係にあります。この機会を利用して覚えておくとよいでしょう。

図5-3.特殊for文

特殊for文

ラッパークラス

サンプルプログラム

インターフェースは、抽象メソッドだけではなく、定数を定義することができます。以下に、インターフェースに定数を定義したサンプルがありまる。実行してみましょう。

SampleClassEx503.java
package exday5;

import java.util.*;

public class SampleEx503 {

	public static void main(String[] args) {
		//	String型でデータを追加
		ArrayList<String> sl = new ArrayList<String>();
		sl.add("ONE");
		sl.add("TWO");
		sl.add("THREE");
		//	特殊for文で結果を出力
		for(String s: sl){
			System.out.print(s+" ");
		}
		System.out.println();	//	改行
		//	Integer型でデータを追加
		ArrayList<Integer> il = new ArrayList<Integer>();
		il.add(1);
		il.add(2);
		il.add(3);
		for(Integer i: il){
			System.out.print(i + " ");
		}
		System.out.println();

	}

}
実行結果
ONE TWO THREE
1 2 3

9行目から16行目は、StringクラスのデータをArrayListに追加し、それを出力しています。そして、19行目から26行目までが、整数のデータを追加・出力しています。

基本データ型とラッパークラス

しかし、ここで一つの問題があります。ArrayListに追加できるデータは、基本的にオブジェクトである必要があります。しかし、整数型intは、クラスではありません。このようなデータを追加するような時に役に立つのが、ラッパークラスです。

ラッパークラスとは、基本データ型をクラスと同じように扱うことができるようにするクラスの総称です。19行目を見てください。

int型のラッパークラスの利用
ArrayList<Integer> il = new ArrayList<Integer>();

<>の中に、Integerという文字列があります。これが、int型のラッパークラスです。つまり、これによって、ArrayListにデータを追加することができるのです。なお、各基本データ型に対応するラッパークラスは、以下のようになっています。(表5-2.)

表5-2.基本データ型とラッパークラス
基本データ型 ラッパークラス
byte Byte
short Short
int Integer
long Long
float Float
double Double
char Character
boolean Boolean

ラッパークラスを利用することにより、整数型でも特殊for文利用できるようになっています。(SampleClassEx503.java23行目~25行目)

また、ラッパークラスは、クラスとしてふるまうとともに、基本データ型としても利用できるという性質があります。 SampleClassEx503.javaの24行目で、System.out.println()で、Integer型であるiを出力していますが、普通の数字として出力されています。

このように、ラッパークラスは、違和感無く基本データ型に変換できるのです。

練習問題 : 問題5.