Rubyで継続渡し

○○言語で継続渡し」シリーズ、今回はRuby。参考文献は『Rubyプログラミング入門』(ISBN:4274063852)。ちょうどp.201にfib関数が載っていたのでそれをベースに一部修正した(これまでと同じアルゴリズムにするため)。

#! /usr/bin/ruby

def fib(n)
  if (n == 1) || (n == 2)
    1
  else
    fib(n - 1) + fib(n - 2)
  end
end

def fib_cps(n, k)
  if (n == 1) || (n == 2)
    k.call(1)
  else
    fib_cps(n - 1, lambda{|v1|
              fib_cps(n - 2, lambda{|v2|
                        k.call(v1 + v2)
                      })
            })
  end
end

(1 .. 9).each do |i|
  puts "Fibonacci(#{i}) = #{fib_cps(i, lambda{|x| x})}"
end

Rubyはあまり使ったことがないんだけど、やっぱり文法が特殊だと感じてしまう。Perlのようでもあり、Lispのようでもあり、部分的にはJavaPascalのようにも見えてそのどれとも違う。特に、「定数.メソッド」という書き方は見る度に毎回軽く驚かされる。要するに慣れなのかな。