What is the best way to tell if a class some_class
is an eigenclass of some object?

- 165,429
- 45
- 277
- 381
3 Answers
(Prior to Ruby 2.0) The following expression evaluates to true
if an only if the object x
is an eigenclass:
Class === x && x.ancestors.first != x
The ===
equality check asserts that x
is an instance of the Class
class, the !=
inequality check uses the fact that the ancestors
introspection method "skips" eigenclasses.
For objects x
that are instances of the Object
class (i.e. x
is not a blank slate object), the Class === x
check is equivalent to x.is_a? Class
or, in this particular case, to x.instance_of? Class
.
Starting with Ruby 2.0, the above expression is not sufficient to detect eigenclasses since it evaluates to true
also for classes that have prepend
ed modules. This can be solved by an additional check that x.ancestors.first
is not such a prepended module e.g. by Class === x.ancestors.first
. Another solution is to modify the whole expression as follows:
Class === x && !x.ancestors.include?(x)

- 378
- 3
- 12
There’s always brute force:
ObjectSpace.each_object.any? {|o| some_class.equal? (class << o; self; end)}

- 171,072
- 38
- 269
- 275
-
I can find the method `eigenclass` defined. On what module is it defined? – sawa Oct 10 '12 at 14:33
-
@sawa Sorry, I had defined it in my irb session. – Josh Lee Oct 10 '12 at 14:40
-
Will `some_class == some_class.ancestors.first` or `some_class.ancestors.first == Class` also work? – sawa Oct 10 '12 at 14:51
-
@sawa That’s also true of `Class`. – Josh Lee Oct 10 '12 at 14:54
-
You are right. So, as long as I consider `Class` as the only exception, it will work? – sawa Oct 10 '12 at 15:05
In 2.1.0 at least, there's Module.singleton_class?
:
Module.singleton_class?
#=> false
Module.new.singleton_class?
#=> false
Class.singleton_class?
#=> false
Class.new.singleton_class?
#=> false
Class.singleton_class
#=> #<Class:Class>
Class.singleton_class.singleton_class?
#=> true

- 3,364
- 3
- 30
- 52