私はRubyでメタプログラミングを学んでおり、method_missingとdefine_methodを介して欠落しているメソッドを定義しようとしています。予期しない動作が発生しているので、誰かがこれを説明できるかどうか疑問に思っています。これが私のクラスです:
class X
def method_missing(m, *args, &block)
puts "method #{m} not found. Defining it."
self.class.send :define_method, m do
puts "hi from method #{m}"
end
puts "defined method #{m}"
end
end
さて、このコード:
x = X.new
x.some_method
puts
x.some_method
puts
puts x
出力を生成します:
method some_method not found. Defining it.
defined method some_method
hi from method some_method
method to_ary not found. Defining it.
defined method to_ary
#<X:0x007fcbc38e5030>
私が得られないのは最後の部分です:なぜRubyはputsの呼び出しでto_aryを呼び出すのですか?Rubyがオブジェクトを印刷するためだけに配列に変換しようとするのはなぜですか?
私はグーグルで調べて、これらの関連リンクを見つけました:
- http://tenderlovemaking.com/2011/06/28/til-its-ok-to-return-nil-from-to_ary/
- http://yehudakatz.com/2010/01/02/the-craziest-fing-bug-ive-ever-seen/
これらはmethod_missingとto_aryの落とし穴についても話しますが、putsがto_aryを呼び出す理由については特に話しません。
また、to_sを定義しても、動作は変わらないことにも言及する必要があります。
def to_s
"I'm an instance of X"
end
「putsx」の出力は次のようになります。
method to_ary not found. Defining it.
defined method to_ary
I'm an instance of X