Java : クロージャ

Delphiクロージャ([id:lethevert:20060110])をやったので、次はJavaでもクロージャをやりたいと思うのですが・・・

      • -

実際は、Javaには、もうほとんどクロージャと読んでもよいものがあるんですよね。つまり、無名クラス。(そういえば、昔も似たようなことを書いているような [id:lethevert:20050825:p2])

interface Closure {
  int call(int in0);
}

class OuterClass {
  Closure add_n(int _n) {
    final n = _n;
    return new Closure() {
      int call(int in0) { return in0 + n; }
    }
  }
}

もし、final変数を経由しないで、ローカル変数にアクセスすることができれば、それはクロージャと呼んでよいものになるはず。逆に、finalがついているせいで、ローカル変数を更新するようなメソッドを作成できないというきつい制限がついてしまって、そのせいで、だいぶ使い勝手が悪くなっています。

      • -

ところで、なんか見難いですね。これで可読性の高いコードを書けといわれると、ちょっと悩むかも。
どの辺が見難いかというと、無名クラスを使っている点じゃないでしょうか? もし、これがこういう風に書ければ、だいぶ見た目は違うのでは?

class OuterClass{
  Closure add_n(int n) {
    return new Add_N_Class();
    
    class Add_N_Class implements Closure {
      int call(int in0) { return in0 + n; }
    }
  }
}

つまり、クロージャに関して、私がJavaにあればいいなと思うのは、メソッド内クラスです。おそらく、無名クラスでfinal変数を要求するのは、無名クラスの実体がクラス内クラスだからじゃないのかと思います。
追記)みずしまさんから突っ込みを受けました。メソッド内クラスは既に存在するそうです。だとすると、やっぱり問題は、final変数しかアクセスできないという点に尽きますね。

      • -

ところで、クロージャについて誤解(?)している人が多い気がします。
[id:nowokay:20060114#1137228975]
http://cappuccino.jp/keisuken/logbook/20060114.html#p06
http://capsctrl.que.jp/kdmsnr/wiki/bliki/?Closure
http://hwb.ecc.u-tokyo.ac.jp/current/CDD1B8ECBDB82FA5AFA5EDA1BCA5B8A5E3.html

      • -

クロージャの適当な定義って、どこかにないかな?
SICP p.98に、↓のようにありますけど、これじゃ分かる人にしか分からないしな。

A closure is an implementation technique for representing procedures with free varialbes.

↓は分かりやすいかも、と思ったけど、そもそも文章として難しいか。
http://min-caml.sourceforge.net/tutorial-mincaml-16.htm
Wikipediaの説明は、わかりやすいかな? 英語が大丈夫な人は、こちらをどうぞ。
http://en.wikipedia.org/wiki/Closure_(computer_science)
これは、日本語で分かりやすいかな?
http://www.geocities.jp/shido_takafumi/lisp/scheme9a.html
要するに、クロージャとは無名関数を作る機能ではなくって、関数内にフリー変数があったときに関数を宣言した環境の変数を参照するという機能なんですよね。