Java.use(better); Episode#01 拡張可能な for 文(1)

前の記事次の記事
Java.use(better);


Episode#01

拡張可能な for 文(1) -- for と別れる50の方法



《関連記事》

Java: 拡張可能な for 文

プログラミング(作譜)の効率化を目指そうとしたとき、朗報に沸いたのが、J2SE 5.0(2004年)での「拡張 for 文〔= enhanced for loop〕」の導入でした。すると、SP の呪縛(反復構造)から解かれて、制御構造の抽象化やポリモフィズムの適用など、OOP の醍醐味を堪能できる環境が整います。これで、Jython/Scala などに遅れを取った Java プログラマーも、彼らと肩を並べられます。

拡張 for 文は、インターフェース Iterable に準拠する任意のクラスと組み合わせて利用できます。すると、データ構造に依存しない抽象表現が可能になるので、コードが簡潔で見通しも良くなります。

情報隠蔽の原則

ソースコードに行番号を付加するときには、テキストファイルの内容を1行ずつ処理します。たとえば、次のように

for (String line: new TextStream(name)) {
  ...

指定した名前 name のファイルの各行 line を参照できます。

このとき、TextStream を利用するプログラマーは、各行を読み込む手段や、ファイルが存在しないときの例外処理などの詳細を知りませんし、知る必要もありません。というのも、その情報は「情報隠蔽の原則」に沿って、TextStream を提供するプログラマーだけが知っていいからです。

□ インターフェース java.util.Iterable

インターフェース Iterable に準拠するメソッドを再定義すると、拡張 for 文を介して「オブジェクトに最適な制御構造」を利用できます。たとえば、拡張 for 文の対象に、Iterable に準拠しないものを指定すると、

_Tips.java:118: foreach は式のタイプに使用できません。
    for (String e: new StringTokenizer("This is a pen.")) {
                   ^

コンパイラーがこれを拒否します。そこで、StringTokenizer をインターフェース Iterable に準拠させて、

    for (String e: new ExTokenizer("This is a pen.")) {
      System.out.println(e);
    }

拡張 for 文を利用すると、次の結果が得られます。

$ java apple.pie._Tips
This
is
a
pen.
$ 

 ̄これは、次のように実現します。

class ExTokenizer extends StringTokenizer
  implements Iterable {
  public ExTokenizer(String str) {
    super(str);
  }
  public Iterator iterator() {
    return new Iterator() {
      public boolean hasNext() { return hasMoreTokens(); }
      public String next()     { return nextToken(); }
      public void remove()     {}
    };
  }
}

ここでは、インターフェース Iterable に準拠するメソッド



と(必要に応じて)インターフェース Iterator に準拠するメソッド群

  • public boolean hasNext()
  • public T next()
  • public void remove()



を再定義します。

 ↑ TOP

update*13/01/03 13:34:41