Bye Bye Moore

猫マンション建築の野望を胸に零細事業主として資本主義の荒波に漕ぎ出したアラサー男の技術メモ

instance_eval()を使うとブロック内でメソッドを呼び出せる

> str = "test"

という文字列があるとします。
これにinstance_evalメソッドをブロック付きで実行すると、追加の文字列を作れます。

> str.instance_eval {|e| "hogehoge %s" % [e]}
=> "hogehoge test"

この程度だと旨味がありませんね。
では、これならどうでしょう??

> str.instance_eval {"hogehoge %s" % [reverse]}
=> "hogehoge tset"

文字列をひっくり返すreverseメソッドを使って愉快な事ができます。
挙げ句の果てに、コレ、インスタンスに対して複数のメソッドまで定義できます。

> puts str.instance_eval { " self\t\t:%s\n reverse\t:%s\n upcase\t\t:%s\n howmany\'t\'\t:%i\n" % [self, reverse, upcase, count('t') ] }
 self		:test
 reverse	:tset
 upcase		:TEST
 howmany't'	:2
=> nil

もうわけがわかりません

自身を返すことも当然できます。
ブロック変数を使うか、selfをつかえばおkです

> str.instance_eval {|e| "hogehoge %s %s %s" % [e, reverse, upcase]}
=> "hogehoge test tset TEST"

> str.instance_eval {"hogehoge %s %s %s" % [self, reverse, upcase]}
=> "hogehoge test tset TEST"

参考もと

Rubyベストプラクティス -プロフェッショナルによるコードとテクニック

Rubyベストプラクティス -プロフェッショナルによるコードとテクニック