Ruby で FizzBuzz を満喫する
Scala にだいぶSAN値を削られたのでここいらで Ruby に日和ろう(苦笑)。
その 1 : Object#tap
を利用する
to_fizzbuzz = -> n { "".tap do |_| _ << "Fizz" if n % 3 == 0 _ << "Buzz" if n % 5 == 0 break n if _.empty? end } puts 1.upto(100).map(&to_fizzbuzz)
Ruby の Object#tap
はブロック内で自分自身に対して行われた破壊的変更が保証される。break
が発動するとそれらの変更を破棄して強制的に別の値を返すことが出来る。発動しなければブロック内で行われた破壊的変更を適用した自身が返ることになる。
さくっと lambda 奴を使っておくと Enumerable#map
に Proc
オブジェクトを渡す Ruby らしい書き方で処理が記述できる。
その 2 : Hash
を利用する
Scala 編で Map
を使ったやつの元ネタ。
Applicators = {3 => :Fizz, 5 => :Buzz} to_fizzbuzz = -> n { fb = Applicators.select{|_| n % _ == 0}.values.join fb.empty? ? n : fb } puts 1.upto(100).map(&to_fizzbuzz)
やってることはほぼ一緒。メソッド名が違うだけ。
その 3 : Enumerable#zip
を利用する
fizz = [nil] * 2 << :Fizz buzz = [nil] * 4 << :Buzz 1.upto(100).zip(fizz.cycle, buzz.cycle) do |n, *f| puts f.any? ? f.join : n end
ネットで見つけてきた。nil
と any
の使い方が Ruby っぽくてお気に入りである。