Consider the following code:
Object subclass: Two []
Two subclass: Three [
superclass [^super class]
]
Three subclass: Five []
Why does Five new superclass
return Five
while Five superclass
returns Three
?
From what I read in the source code of the Object class in both Dolphin Smalltalk and GNU Smalltalk, the class
uses self
which is why Five new superclass
returns Five
. I do not understand why Five superclass
returns Three
, however.
I'm using an online version of the GNU Smalltalk interpreter.
Let's depict the hierarchy
Object
Two
Three
Five
Also, we have the (instance side) method
Three >> superclass
^super class
First of all, let's recall that Five superclass
is Three
just because Five
is a direct subclass of Three
(nothing special here).
Now let's see why Five new superclass
answers with Five
instead. For this we need to closely analyze the superclass
method above.
Since the message #class
is implemented at the top of the hierarchy (every object knows how to answer its class
), the method at Three
just refers to the inherited class
method implemented in Object
. Hence, Three >> superclass
is essentially equivalent to class
(it does nothing but invoking the inherited method class
which it already got "for free"). Finally, since Five
inherits from Three
, when we send superclass
to any of its instances (Five new superclass
), we get the same we would have gotten for any instance of Three
(inheritance again), which is the class
of the instance which receives the message, Five
in this case.
What might be confusing here is the use of super
in Three >> superclass
. But in this case super
is entirely equivalent to self
. It wouldn't have been, had Three
implemented class
in a way different from the one inherited from Object
(which it didn't). So in fact, the method is equivalent to
Three >> superclass
^self class
meaning that for instances and subinstances of Three
asking their superclass
is the same as asking for their class
.
Another piece of confusion comes from the tricky selector chosen: superclass
. By default, superclass
is a message understood by classes, not instances. However, the trick here is to implement the same selector on the instance side of the class to bring confusion on purpose (and test your orientation). This is confusing because when we see superclass
our brains "automatically" connect with the class that is above me. But that is only true if you are speaking to the class, not to any of its instances.
To further uncover the trick, let's rename the selector to something less special
Three >> foo
^super class
and then try Five new foo
, which will answer Five
just because Five new
is an instance of Five
.