forked from pharo-project/pharo
-
Notifications
You must be signed in to change notification settings - Fork 0
/
ExampleSlotWithState.class.st
60 lines (43 loc) · 1.47 KB
/
ExampleSlotWithState.class.st
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
"
I am a simple example for a Slot.
Instead of mapping to a field, I store the value myself. This means that all instances share the
slot, similar to a class variable.
I just overide the methods for reflective read and write (#read and #write:to:), I do not bother to emit bytecode myself but rely on the fallback that the compiler will generate code for reflective read and write (see the emit* method of my superclass).
Smalltalk classInstaller make: [ :builder |
builder name: #A;
slots: { ExampleSlotWithState named: #iv };
category: #Playground ].
In class A we can implement accessors:
iv
^iv
iv: anObject
iv := anObject
They look like normal ivar accesses, but in the background, the compiler delegated to the Slot the code generation, calling emit*, which leads
to the bytecode e.g. for the read:
21 <20> pushConstant: iv => TestSlot
22 <70> self
23 <E1> send: read:
24 <7C> returnTop
you could override the emit* methods to generate faster code, but to get something running it is not needed.
To test, e.g. you can set the slot from one object and read it from another:
A new iv: 6
A new iv
Then inspect the slot:
(A slotNamed: #iv) inspect
"
Class {
#name : #ExampleSlotWithState,
#superclass : #Slot,
#instVars : [
'value'
],
#category : #'Slot-Examples-Base'
}
{ #category : #'meta-object-protocol' }
ExampleSlotWithState >> read: anObject [
^ value
]
{ #category : #'meta-object-protocol' }
ExampleSlotWithState >> write: aValue to: anObject [
value := aValue
]