1
class Class
  def mixin_ancestors(include_ancestors=true)
    ancestors.take_while {|a| include_ancestors || a != superclass }.
    select {|ancestor| ancestor.instance_of?(Module) }
  end
end

class MyTestClass

end

Took the above code from How do you list included Modules in a Ruby Class?

I have following questions.

1) By saying 'def mixin_ancestors' as in the above code we are defining an instance method. But doing 'a = MyTestClass.new ; a.mixin_ancestors' says undefined method mixin_ancestors.

2) So I did ‘MyTestClass. mixin_ancestors’. It gave me a list .

3) I think ‘ancestors’ is a method. In which context does the ‘ancestors’ method runs. To find that I did ‘method(ancestors).owner’ but got error- method: [MyTestClass, Object, Kernel, BasicObject] is not a symbol (TypeError). Got this trick from my own previous question Determine the class to which a method belongs in rails

4) Like third point on which context does superclass method in the above code runs.

Thanks for the helps

Community
  • 1
  • 1
Rajkamal Subramanian
  • 6,884
  • 4
  • 52
  • 69

2 Answers2

2

1 & 2) We are defining an instance method of Class which means it will be a class method for other objects.

3) It is run within Class object, so it is a method of Class or one of it's ancestors (it's actually in BasicObject)

4) It is run in context of Class object (or of object extending it)

Mchl
  • 61,444
  • 9
  • 118
  • 120
  • My understanding from your answer is. The context (that is self) inside `mixin_ancestors` points to `MyTestClass` which is an instance of `Class`. By calling methods like `ancestors`,`superclass` inside `mixin_ancestors` we are actually invoking these methods on `MyTestClass` itself. `MyTestClass` got the `superclass` method at its class level from `Class`, where it should be defined at instance level. `MyTestClass` got the `ancestors` method at its class level from `Module`, where it should be defined at instance level. – Rajkamal Subramanian Sep 06 '11 at 09:29
  • That seems to be correct. The key is to remember that classes are objects in Ruby too. – Mchl Sep 06 '11 at 09:34
0

In ruby, Class is a class for class object. In your example, MyTestClass is an instance of class Class. So, mixin_ancestor is an instance method for these objects.

In 3), you should use method(:ancestors), but you simply call it - and it returned an array - as you can see in output - [MyTestClass, Object, Kernel, BasicObject]

4) self here is an instance of Class

I strongly recommend you to buy http://www.amazon.com/Metaprogramming-Ruby-Program-Like-Pros/dp/1934356476 - this book explains ruby in excellent way!

Sławosz
  • 11,187
  • 15
  • 73
  • 106