やっとgroovyの話です

ただこれまで書いたことがGroovyで有効に使えるかといったら、それはNOだと思います。よく考えてみるとクロージャをネストさせればそのぶんの無名クロージャオブジェクトが生成されるコストがかかるはずなので、純粋関数型な言語でなければYコンビネータやらZコンビネータをGroovyクロージャでやるのはあんまりメリットが感じられないからです。

Groovyらしくクロージャをつかって、キャッシュ機能をもりこんでおなじものをやるならこんなかんじになるのではと思います。

def cached_fib = {
  def cache = new HashMap()
  return {n->
    if(n==0 || n==1){
      return 1
    }else{
      if(cache[(n-1).toString()]==null){
        cache[(n-1).toString()] = call(n-1)
      }
      if(cache[(n-2).toString()]==null){
        cache[(n-2).toString()] = call(n-2)
      }
      return cache[(n-1).toString()]+cache[(n-2).toString()]
    }
  }
}()

def s3 = System.currentTimeMillis()
println "ans: "+cached_fib(40)
println "キャッシュつき再帰クロージャ: ${((System.currentTimeMillis()-s3)/1000)} sec"

実行してみると…

ans: 165580141
キャッシュつき再帰クロージャ: 0.003 sec

もう笑うしかないですね。