[ANN] Article: Seeing Metaclasses Clearly

  • Thread starter why the lucky stiff
  • Start date
T

ts

C> Before your discoveries make you jump into conclusions, you should apply a
C> little of scientific thought. You have two facts: one, that the diagram
C> shows that Object --instanceof--> (Object). The other: that

More I follow this discussion, more I've problem.

Where do you see (except in a book which don't describe the ruby object
model) that the diagram show

"Object --instanceof--> (Object)"

It's clearly stated

Classes in Ruby are first-class objects---each is an instance of
class +Class+.

and it don't exist an horizontal arrow for this case.


Guy Decoux
 
C

Carlos

C> Before your discoveries make you jump into conclusions, you should apply a
C> little of scientific thought. You have two facts: one, that the diagram
C> shows that Object --instanceof--> (Object). The other: that

More I follow this discussion, more I've problem.

Where do you see (except in a book which don't describe the ruby object
model) that the diagram show

"Object --instanceof--> (Object)"

It's clearly stated

Classes in Ruby are first-class objects---each is an instance of
class +Class+.

and it don't exist an horizontal arrow for this case.

Noo... I didn't see that anywhere, I wrote this in my diagram. Is it wrong?

I saw that rb_obj_is_instance_of does:

if (rb_obj_class(obj) == c) return Qtrue;

and rb_obj_class does:

return rb_class_real(CLASS_OF(obj));

and rb_class_real does:

while (FL_TEST(cl, FL_SINGLETON) || TYPE(cl) == T_ICLASS) {
cl = RCLASS(cl)->super;
}

So I thought it was skipping the singleton classes. Or isn't it?

search_method, on the other hand, doesn't skip anything.

From the above I deduced the diagram. In which step should I have applied a
little more scientific thinking? :) Where does ruby search for methods, if
not in the inheritance chain?
 
C

Chris Pine

One possible explanation for this discrepancy is that the diagram is wrong.
instance_of? tells you (accurately, definitively) whether or not
something is an instance of something. Obviously you can draw a
diagram that posits any relationship you wish.

Then what do the sideways arrows in the 'ri Class' documentation mean?
Carlos didn't draw that diagram, and he isn't making that up.
Clearly, there's a meaningful relationship there.

See again the 'klass' arrow on page 384 (Figure 24.3) of the Pickaxe2.

If "instance_of? tells you (accurately, definitively) whether or not
something is an instance of something", then it sounds like you
defining the instance of something to be "that which is returned by
instance_of?".

It seems to me that there are two very different relationships here:
what I will call "instance" (though David might not like how I will
use it) and what I will call "superclass". These are the arrows used
both in 'ri Class' and in the pickaxe, and I think these are the
meaningful relationships. (Usually, the relationship one-to-many
relationship of 'kind_of?' is what we want, but that is built out of
one "instance" relationship, and zero-or-more "superclass"
relationships.)

When you create a singleton class for an object, you are changing the
'klass' pointer and, as I see it, changing which class it is an
instance of. What is returned by "instance_of?" does not change (and
I'm complaining about that, mind you; I'm fine with how it works), but
that object's immediate "papa" has changed.

I would also argue (I mean, it's almost the same statement) that the
objects class has changed, despite the fact that method 'class' still
returns the original class.

I think that's what Carlos is saying, and I think he's right. (And if
that's not what he's saying, then... um... I think *I'm* right! :)

I thought that the reason these methods didn't reflect the
singleton-ness under the skin of Ruby was that matz didn't want us
mucking around there. As I recall, he thought of it as an
implementation, but that he might want to change that some day. (I
think it's more of a necessity of the language than an implementation
detail, personally. When I saw that (Object)'s superclass was Class,
my mind was opened. :)

Chris
 
T

ts

C> When you create a singleton class for an object, you are changing the
C> 'klass' pointer and, as I see it, changing which class it is an
C> instance of. What is returned by "instance_of?" does not change (and
C> I'm complaining about that, mind you; I'm fine with how it works), but
C> that object's immediate "papa" has changed.

You are speaking about implementation details.

If I remember well, matz has said one day that he can completely implement
ruby without the need of the singleton class.

Forget the singleton class, for the moment :)


Guy Decoux
 
D

David A. Black

Hi --

Then what do the sideways arrows in the 'ri Class' documentation mean?
Carlos didn't draw that diagram, and he isn't making that up.
Clearly, there's a meaningful relationship there.

I'm uneasy with the explanation that "instance_of? doesn't take into
account singleton classes", because, as I read it, it seemed to
suggest that what instance_of? returns is irrelevant to the question
of whether or not something is an instance of something else. I'd
rather trust the method; otherwise, I don't know where to start or
stop second-guessing the meta-information that Ruby gives me.
See again the 'klass' arrow on page 384 (Figure 24.3) of the Pickaxe2.

If "instance_of? tells you (accurately, definitively) whether or not
something is an instance of something", then it sounds like you
defining the instance of something to be "that which is returned by
instance_of?".

instance_of? returns true or false; I'm just taking that literally.
It seems to me that there are two very different relationships here:
what I will call "instance" (though David might not like how I will
use it) and what I will call "superclass". These are the arrows used
both in 'ri Class' and in the pickaxe, and I think these are the
meaningful relationships. (Usually, the relationship one-to-many
relationship of 'kind_of?' is what we want, but that is built out of
one "instance" relationship, and zero-or-more "superclass"
relationships.)

The arrows in ri Class are inheritance are described as representing
inheritance, not instance-ness. (And all these relationships are
meaningful -- we're just talking terminology :)
When you create a singleton class for an object, you are changing the
'klass' pointer and, as I see it, changing which class it is an
instance of. What is returned by "instance_of?" does not change (and
I'm complaining about that, mind you; I'm fine with how it works), but
^^^^^^^^^^^^^^^

? :)
that object's immediate "papa" has changed.

And that's definitely a significant operation. It just doesn't seem
to entail a change at the "what this is an instance of" level. I can
imagine a definition or adaptation of "instance" that did refer to
both, but it appears that Matz's choice is to have the "instance of"
relationship apply only to the relationship between an object and its
"birth class".

To put it another way: in describing what happens when a singleton
class is created, it seems to me to be problematic to choose a term
which, immediately, Ruby is going to tell you is wrong. Certainly
there should be terminology for all of this (or perhaps the problem is
there's too much :) and it's all important. I just don't want to
create a terminological inconsistency that then has to be sort of
re-explained or "asterisked" every time it comes up.

Whoops, I deleted the thing where you said that you would argue that
an object's class changes when its singleton class is created....
This is why I want Kernel#singleton_class (or Object, or wherever) --
because it's not an either-or choice. They both exist, and they
should both be (easily) referable to. I would actually be happy with
#class becoming #birth_class, and being paired with #singleton_class
(or #own_class), but one thing at a time :)


David
 
C

Chris Pine

I'm uneasy with the explanation that "instance_of? doesn't take into
account singleton classes", because, as I read it, it seemed to
suggest that what instance_of? returns is irrelevant to the question
of whether or not something is an instance of something else. I'd
rather trust the method; otherwise, I don't know where to start or
stop second-guessing the meta-information that Ruby gives me.

Yeah, I can definitely see your point. My view is that, in actual,
practical code, don't use 'class' or 'instance_of?' at all, use
'kind_of?'. That's almost certainly what you want, and it does take
into account singleton classes and modules (another aspect of all of
this we are leaving out). Though, if you can avoid 'kind_of?' and
just use your duck typing and unit testing, of course that's the best
thing. :)

But if you are playing around with meta-info in Ruby, it kind of seems
like you have to distrust 'class' and 'instance_of' for these reasons.
Or at least make it clear that you mean "birth class" and not "first
class in the list of things this object is a 'kind_of?'" But who
wants to give those sorts of qualifiers all over? :)

instance_of? returns true or false; I'm just taking that literally.

Well, it seems like some interpretation is perhaps called for. As has
been noted, 'Object.superclass' return 'nil'... and we don't want to
take that too literally! <chuckle, chuckle>

<chuckle>

(I'm sorry, but that really cracked me up...)

<chuckle>

Oh, boy. If anyone else here thinks I'm half as funny as *I* think I
The arrows in ri Class are inheritance are described as representing
inheritance, not instance-ness.

Actually, though they are not listed as such, the sideways arrows do
not. Classes cannot have two superclasses, and a class's relationship
to it's superclass is really nothing like it's relationship to it's
singleton class (which is much more line an instance-ness
relationship).

For my OSCON talk on the Ruby Object Model (back in 2003), I used
different colored arrows for that particular picture. That really
helps a lot.

(And all these relationships are
meaningful -- we're just talking terminology :)

Very true.

^^^^^^^^^^^^^^^

NOT complaining! NOT AT ALL complaining! Yikes...

but it appears that Matz's choice is to have the "instance of"
relationship apply only to the relationship between an object and its
"birth class".

Yes, it does appear that way. I think it's a mistake how he has tried
to hide this stuff "under the rug" as it feels to me. On the other
hand, I'd have made far more mistakes in making a language, and in
practice this stuff never comes up at all.

If I were to do some serious metaclass hackery, I would certainly not
be using 'class' and 'instance_of?' anywhere. I'd use why's tools.
If I were just trying to explain how the Ruby object model works
(something I have thought a fair bit about), I would similarly avoid
them, instead talking about 'kind_of?'. And in all other cases, duck
typing is the way to go.

Given all of that, 'class' and 'instance_of?' don't seem like very
useful methods as they work now.

I just don't want to
create a terminological inconsistency that then has to be sort of
re-explained or "asterisked" every time it comes up.

Amen! Although, I feel like this is already the case... :)

"Well, Ruby does say that the class is String, and we know that when
Ruby checks for methods, it starts with the class, then moves up the
inheritance chain... but really, it starts with the singleton class,
then up to any included modules in reverse order that they were
included, *then* up to String and so on..."

I feel like to really explain the topic, you kind of have to say all that.

This is why I want Kernel#singleton_class (or Object, or wherever) --
because it's not an either-or choice. They both exist, and they
should both be (easily) referable to.
Agreed.


I would actually be happy with
#class becoming #birth_class, and being paired with #singleton_class
(or #own_class), but one thing at a time :)

Yeah... I'm not sure. I'm fine with it as it is, I guess because it
looks easy to a beginner (which is important for a tutorial writer
like me). It is an over-simplification, but on the surface it makes
sense. Then, when you dig down, you learn that 'class' is, in
whatever sense, not telling you the "whole" truth. That's fine, too,
because at that point you are fairly advanced, and can handle it.

I think it's great that you can do a lot of Ruby *without* having to
know this stuff.

Chris
 
D

David A. Black

Hi --

Well, it seems like some interpretation is perhaps called for. As has
been noted, 'Object.superclass' return 'nil'... and we don't want to
take that too literally! <chuckle, chuckle>

I think interpreting false as true in this case is a bit of a stretch
:) I'm not "against" the idea of an object being an instance of its
singleton class in some general way. In fact, I'm fairly certain that
I once wrote something along the lines of: every object is an instance
of two classes... etc., somewhere. But if that's wrong, it's wrong; I
don't want to second-guess it.
Amen! Although, I feel like this is already the case... :)

"Well, Ruby does say that the class is String, and we know that when
Ruby checks for methods, it starts with the class, then moves up the
inheritance chain... but really, it starts with the singleton class,
then up to any included modules in reverse order that they were
included, *then* up to String and so on..."

I feel like to really explain the topic, you kind of have to say all that.

But just don't tie yourself in that knot in the first place, and then
you don't have to untie it :) If you never say "we know that when
Ruby checks for methods, it starts with the class...." then you never
have to back out of it.
Yeah... I'm not sure. I'm fine with it as it is, I guess because it
looks easy to a beginner (which is important for a tutorial writer
like me). It is an over-simplification, but on the surface it makes
sense. Then, when you dig down, you learn that 'class' is, in
whatever sense, not telling you the "whole" truth. That's fine, too,
because at that point you are fairly advanced, and can handle it.

I think it's great that you can do a lot of Ruby *without* having to
know this stuff.

On the other hand (also from the point of view of a chronic
explainer of Ruby :) it's easier to say: Every object has a birth
class and a singleton [or whatever] class, than: Every object has a
class and a (class << self; self; end) :)


David
 
J

Jim Weirich

David A. Black said:
On the other hand (also from the point of view of a chronic
explainer of Ruby :) it's easier to say: Every object has a birth
class and a singleton [or whatever] class, than: Every object has a
class and a (class << self; self; end) :)

A question for those familiar with Ruby internals ... does an object's
singleton class exist from the moment the object is created, or does it
spring into existence the moment it is needed to hold singleton methods?
 
D

David A. Black

Hi --

David A. Black said:
On the other hand (also from the point of view of a chronic
explainer of Ruby :) it's easier to say: Every object has a birth
class and a singleton [or whatever] class, than: Every object has a
class and a (class << self; self; end) :)

A question for those familiar with Ruby internals ... does an object's
singleton class exist from the moment the object is created, or does it
spring into existence the moment it is needed to hold singleton methods?

I'm pretty sure it springs into existence for the purpose, just to
avoid overpopulating object space with classes. Otherwise there would
be, say, 10000 class objects created for an array of 10000 one-byte
strings, etc. (This is based partly on some familiarity with
internals and also memory of previous discussions with people with
more familiarity with internals.)


David
 
P

Peter Suk

Hi --



I'm pretty sure it springs into existence for the purpose, just to
avoid overpopulating object space with classes. Otherwise there would
be, say, 10000 class objects created for an array of 10000 one-byte
strings, etc. (This is based partly on some familiarity with
internals and also memory of previous discussions with people with
more familiarity with internals.)

That would be very hard on GC, since you'd also be creating 10000 new
'roots' to start traversing from.

--Peter
 
C

Chris Pine

Otherwise there would
be, say, 10000 class objects created for an array of 10000 one-byte
strings, etc.

Well, it would be worse than that, actually, since singleton classes
are themselves objects, and can have their own singleton classes...

So just having a single object would cascade into an infinite tower of
singleton classes, until you ran out of memory.

However, I think that when you create a class with "def class", it
always creates the singleton class then.

Chris
 
G

gabriele renzi

ts ha scritto:
C> When you create a singleton class for an object, you are changing the
C> 'klass' pointer and, as I see it, changing which class it is an
C> instance of. What is returned by "instance_of?" does not change (and
C> I'm complaining about that, mind you; I'm fine with how it works), but
C> that object's immediate "papa" has changed.

You are speaking about implementation details.

If I remember well, matz has said one day that he can completely implement
ruby without the need of the singleton class.

Forget the singleton class, for the moment :)

ah! this is something I always wanted to know, I've been always thinking
on the lines of "why are'nt method just defined in the object? do we
need this singleton class thing?"
 
L

Lyndon Samson

Maybe we should change the subject of this thread?

Since there is no such thing as metaclasses in ruby ;-)

<quote>
|I've been trying to understand metaclasses

You don't have to, because there's no such a thing in Ruby.
In Smalltalk, a metaclass is a class of a class.

In Ruby, the Class class is the class of all classes, no metaclass.
But every object (of course including classes) can have hidden
meta-object (the place holder for singleton methods), which is only
revealed by the "singleton class notation".
</quote>

from http://www.ruby-talk.org/cgi-bin/scat.rb/ruby/ruby-talk/40537
 
T

ts

g> ah! this is something I always wanted to know, I've been always thinking
g> on the lines of "why are'nt method just defined in the object? do we
g> need this singleton class thing?"

Well, if you want a more stupid explanation (it's easy for me to be stupid
:))

* a module is an object which can store (define) methods

* a class is a module which can use inheritance

* for classes, you have
- "birth" class which can create instance

- "singleton" class which is always associated with only one object

and no, a "singleton" class is not a "birth" class.

And in smalltalk terminology, ruby has only one metaclass : it's Class.



Guy Decoux
 
C

csaba

David said:
I always thought it was singleton in the sense that, unlike the "birth
class", it was not shared with other objects. There is of course a
long history of discussion about the term "singleton", and the fact
that it's overloaded.... I've suggested "own class", and others have
suggested other terms, though I don't know that even a pronouncement
from Matz will change usage completely.

"Own class" is the best I've heard 'till now in terms of correctness,
it's just a bit "pale". I mean, when you say "I go there by my own
car", then the "own" doesn't refer to a special type of car, it just
refers to some relation of the car with other things. It refers to a
non-intrinsic thing. But if you say
"I go there by my batcar", that makes a difference. Such a thing is
what we need for ruby.

What about "eigenclass", like in eigenvalue?
 
M

Mark Hubbart

"Own class" is the best I've heard 'till now in terms of correctness,
it's just a bit "pale". I mean, when you say "I go there by my own
car", then the "own" doesn't refer to a special type of car, it just
refers to some relation of the car with other things. It refers to a
non-intrinsic thing. But if you say
"I go there by my batcar", that makes a difference. Such a thing is
what we need for ruby.

What about "eigenclass", like in eigenvalue?

I think you're right about "own class". The most defining
characteristic of "singleton classes" is probably not that they only
have one instance, but that only one instance has *them* :) They are
the personal, or private class of that object. a jaunt through a
thesaurus gives a few possible synonyms for "own class":
- personal class
- private class
- exclusive class
- reserved class

I'm not sure "personal" works when referring to objects (or classes);
it sounds like an attempt to anthropomorphize them.
"private" might be good, though it might be confusing, what with
public/private methods. But it couldn't be more confusing than
"singleton class" vs "Singleton class" :)
"exclusive", I'm not sure if it sounds right, or has the right shade
of meaning. "reserved" either.

What do you think of "private class"? Or is there some other
definition I'm missing that would preclude that? Would that be a good
overloading of terms?

cheers,
Mark
 
T

Trans

What do you think of "private class"? Or is there some other
definition I'm missing that would preclude that? Would that be a good
overloading of terms?

Problem with that is a concept that has been foward for classes that
are not visible outside a given scope. eg.

class X
private class Y
# ...
end
# ...
end

Not that Ruby has them (yet ;-) but that would most certainly be
called a "private class".

I had been holding on to the term "special class", but I suppose that
makes it sound like it has "special" needs :) Perhaps we should try a
differnt tact, like "root class" or "direct class".

T.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,755
Messages
2,569,536
Members
45,009
Latest member
GidgetGamb

Latest Threads

Top