それマグで!

知識はカップより、マグでゆっくり頂きます。 takuya_1stのブログ

習慣に早くから配慮した者は、 おそらく人生の実りも大きい。

Emunrable#each に関数・メソッド・Procを渡す。

irb でチマチマ考えながら作ってると、each/mapなどのブロックの内部を修正したりが面倒になってくるので、簡単にやりたかった。

通常の Enumerable#each

eachはブロック渡すように習います。

["a","b","c"].each{|e| puts e}

Procも渡せます。

もちろんProcも渡せます。

my_proc = Proc.new{|e| puts e }
["a","b","c"].each(&my_proc)

Procオブジェクトを渡せばProc#call されて実行されます。

関数も渡せます

Proc渡せるなら、Functionも渡したい

def my_func(e)
  puts e
end
["a","b","c"].each(&Object.method(:my_func))

グローバルにかいた関数は、グローバルなObjectのmethodとして定義されているので、Object#method[:symbol]で取得できる
グローバルなObject(Kernel)は省略可能なので

["a","b","c"].each(&method(:my_func))

でも同じ。
変数のコンテキストが若干変わるが、to_procも使える

my_proc = method(:my_func).to_proc
["a","b","c"].each(&my_proc)

クラスのメソッド呼び出したい。

配列の要素のメソッドを順番に呼び出すだけならもっと簡単に。

["a","b","c"].map(&:bytes).map(&:to_a)
#=> [[97], [98], [99]]

こんなふうに書くことが出来る

単純なメソッド呼び出しならblockにProcいれる

Blockも勿論便利なんだけど、

  1. 再利用が出来る
  2. irb から使うのに便利
  3. 大きなメソッドチェインの一部を書き換えて、dumpしたい

などという時に便利でした。楽ちん


関数と、メソッドとProcはそれぞれ変数のコンテキストが違うので、使い分けにも便利。