Attr_accessor/_reader/_writer and method_defined?

Why does a method defined using attr_accessor/_reader/_writer is not
found by .method_defined? For example:

$ irb
irb(main):001:0> require ‘pp’
=> true
irb(main):002:0> PP.method_defined? :pp
=> true
irb(main):003:0> PP.method_defined? :sharing_detection
=> false
irb(main):004:0> PP.respond_to? :sharing_detection
=> true

···


dave

My guess:

Taking a peek at pp.rb, #pp is defined for several things, including Kernel.
Kernel methods get included in everything, which means everything gets an
instance method #pp.

I’m guessing that #method_defined? tells you if objects of the given Module
have a given instance method. #sharing_detection is an accessor for the
class instance variable @sharing_detection of PP, defined as:

class << PP
attr_accessor :sharing_detection
end

Or some such. This means that the class in which the method is defined is
the singleton class of PP, accessed by:

class << PP; self; end

Sure enough, if you call method_defined? on the singleton class, you get
true.

So:

PP responds to #sharing_detection, but it’s defined in its singleton class.
PP defines a method #pp, so objects of class PP will respond to #pp.
Kernel defines a method #pp so objects including Kernel will respond to #pp.

Hope this clears things up.

  • Dan