Hi,
from reading the HyperSpec it seems not to be required that
SLOT-VALUE works for structures. But most implementations
are supporting this feature, I'd guess.
Q: is there any CL implementation that does not allow SLOT-VALUE
to be used with structures?
Regards,
Rainer Joswig
--
http://lispm.dyndns.org/
Rainer Joswig wrote:
> Hi,
>
> from reading the HyperSpec it seems not to be required that
> SLOT-VALUE works for structures.
No, that's incorrect.
From the description of SLOT-VALUE:
"The specific behavior depends on object's metaclass. An error is never
signaled if object has metaclass standard-class. An error is always
signaled if object has metaclass built-in-class. The consequences are
unspecified if object has any other metaclass--an error might or might
not be signaled in this situation. Note in particular that the behavior
for conditions and structures is not specified."
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
In article <···············@mid.individual.net>,
Pascal Costanza <··@p-cos.net> wrote:
> Rainer Joswig wrote:
> > Hi,
> >
> > from reading the HyperSpec it seems not to be required that
> > SLOT-VALUE works for structures.
>
> No, that's incorrect.
>
> From the description of SLOT-VALUE:
>
> "The specific behavior depends on object's metaclass. An error is never
> signaled if object has metaclass standard-class. An error is always
> signaled if object has metaclass built-in-class. The consequences are
> unspecified if object has any other metaclass--an error might or might
> not be signaled in this situation. Note in particular that the behavior
> for conditions and structures is not specified."
"Note in particular that the behavior
for conditions and structures is not specified"
What does that mean? That SLOT-VALUE for structures
might or might not work?
>
>
> Pascal
--
http://lispm.dyndns.org/
Rainer Joswig <······@lisp.de> writes:
> "Note in particular that the behavior
> for conditions and structures is not specified"
>
> What does that mean? That SLOT-VALUE for structures
> might or might not work?
Yes. Literally. It might, or might not work. It's not specified.
--
__Pascal Bourguignon__ http://www.informatimago.com/
CAUTION: The mass of this product contains the energy equivalent of
85 million tons of TNT per net ounce of weight.
In article <··············@hubble.informatimago.com>,
···@informatimago.com (Pascal J. Bourguignon) wrote:
> Rainer Joswig <······@lisp.de> writes:
> > "Note in particular that the behavior
> > for conditions and structures is not specified"
> >
> > What does that mean? That SLOT-VALUE for structures
> > might or might not work?
>
> Yes. Literally. It might, or might not work. It's not specified.
Isn't that what he said in his original post? He wrote "not to be
required that SLOT-VALUE works for structures". If it might not work
then it's not required that it work. He didn't say "required NOT to
work".
--
Barry Margolin, ······@alum.mit.edu
Arlington, MA
*** PLEASE post questions in newsgroups, not directly to me ***
*** PLEASE don't copy me on replies, I'll read them in the group ***
On Jun 27, 1:04 am, ····@informatimago.com (Pascal J. Bourguignon)
wrote:
> Rainer Joswig <······@lisp.de> writes:
> > "Note in particular that the behavior
> > for conditions and structures is not specified"
>
> > What does that mean? That SLOT-VALUE for structures
> > might or might not work?
>
> Yes. Literally. It might, or might not work. It's not specified.
... which makes a CDR mandatory. Another bit of fixing that the ANSI
spec needs. I really, really do not see why SLOT-VALUE should not
work for structures (and why we should not be able to figure out which
slots are in a structure).
Cheers
--
Marco
Marco Antoniotti <·······@gmail.com> writes:
> On Jun 27, 1:04 am, ····@informatimago.com (Pascal J. Bourguignon)
> wrote:
> > Rainer Joswig <······@lisp.de> writes:
> > > "Note in particular that the behavior
> > > for conditions and structures is not specified"
> >
> > > What does that mean? That SLOT-VALUE for structures
> > > might or might not work?
> >
> > Yes. Literally. It might, or might not work. It's not specified.
>
> ... which makes a CDR mandatory. Another bit of fixing that the ANSI
> spec needs. I really, really do not see why SLOT-VALUE should not
> work for structures (and why we should not be able to figure out which
> slots are in a structure).
The historical reason is probably not what you think. The original
reason was that some vendors (Gold Hill was an example, I think)
didn't to trust that CLOS would be there... they were afraid it would
not be popular ... but in any case, regardless, they wanted for the
sake of small address spaces to be able to tree-shake it. So Gold
Hill wanted not to have specified that CLOS was involved for errors,
and it wanted structures to be nice and clean and simple so they could
be mostly compiled out and ultra-cheap at runtime. The problem is
that the inclusion of SLOT-VALUE vaguely implies the inclusion of
relevant support for reflection, which means having on-board metadata
that could, and in some implementations would, be compiled out. Even
in the modern world, for embedding, this might be useful. But it
probably suffices to have a SLOT-VALUE-free subset (if not a MOP-free
subset) in that case. And it's probably somewhat the case that the
concern about small address spaces, while noble, is less relevant
these days--not totally unimportant, but no longer a big deal. Lisp
is probably no match for last night's John Stewart show on most
people's disk... Although in its time, Lisp was losing popularity left
and right because of its size and Gold Hill was one of the strongest
voices for tightening things up in that regard because they had some
of the strongest resource issues.
So I don't disagree with getting vendors to agree. But I do, just on
principle, disagree with your use of the word "mandatory". I would
substitute the less emotionally strong but mostly functionally
equivalent word "reasonable".
Kent M Pitman <······@nhplace.com> wrote:
> So I don't disagree with getting vendors to agree. But I do, just on
> principle, disagree with your use of the word "mandatory". I would
> substitute the less emotionally strong but mostly functionally
> equivalent word "reasonable".
But note that even with a *mandatory* CDR, it is only *reasonable* to
hope that vendors will implement it ;-)
--
5th European Lisp Workshop at ECOOP 2008, July 7: http://elw.bknr.net/2008/
Didier Verna, ······@lrde.epita.fr, http://www.lrde.epita.fr/~didier
EPITA / LRDE, 14-16 rue Voltaire Tel.+33 (0)1 44 08 01 85
94276 Le Kremlin-Bic�tre, France Fax.+33 (0)1 53 14 59 22 ······@xemacs.org
On Jun 27, 10:25 am, Didier Verna <······@lrde.epita.fr> wrote:
> Kent M Pitman <······@nhplace.com> wrote:
>
> > So I don't disagree with getting vendors to agree. But I do, just on
> > principle, disagree with your use of the word "mandatory". I would
> > substitute the less emotionally strong but mostly functionally
> > equivalent word "reasonable".
>
> But note that even with a *mandatory* CDR, it is only *reasonable* to
> hope that vendors will implement it ;-)
Yep. Actually, I just meant to mis-paraphrase Kant. It is a
"categorical imperative" :) to write a CDR. Then it is up to the
implementors to decide what to do.
Cheers
--
Marco
Pascal Costanza wrote:
> Rainer Joswig wrote:
>> Hi,
>>
>> from reading the HyperSpec it seems not to be required that
>> SLOT-VALUE works for structures.
>
> No, that's incorrect.
I'm terribly sorry - I misread your OP: I missed the "not".
My apologies.
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
Rainer Joswig <······@lisp.de> writes:
> Hi,
>
> from reading the HyperSpec it seems not to be required that
> SLOT-VALUE works for structures. But most implementations
> are supporting this feature, I'd guess.
>
> Q: is there any CL implementation that does not allow SLOT-VALUE
> to be used with structures?
It doesn't work in emacs-cl 0.8:
COMMON-LISP-USER> (PROGN (DEFSTRUCT S (F 42)) (SLOT-VALUE (MAKE-S) 'F))
Debugger invoked on condition #<UNDEFINED-FUNCTION {12346}>
Available restarts:
0 ABORT
Type "r <n>" or just "<n>" to in invoke a restart,
and "b" to print a backtrace.
b
Backtrace:
ad-Orig-backtrace()
backtrace()
INVOKE-DEBUGGER([UNDEFINED-FUNCTION nil])
ERROR(UNDEFINED-FUNCTION)
cl-debugger(error (void-function SLOT-VALUE-USING-CLASS))
SLOT-VALUE-USING-CLASS([STRUCTURE-CLASS [S (STRUCTURE-OBJECT) nil nil nil nil nil nil nil nil]] [S 42] F)
eval-with-env((SLOT-VALUE (MAKE-S) (QUOTE F)) [environment nil nil nil nil nil nil nil nil])
eval-body(((DEFSTRUCT S (F 42)) (SLOT-VALUE (MAKE-S) (QUOTE F))) [environment nil nil nil nil nil nil nil nil])
eval-with-env((PROGN (DEFSTRUCT S (F 42)) (SLOT-VALUE (MAKE-S) (QUOTE F))) nil)
EVAL((PROGN (DEFSTRUCT S (F 42)) (SLOT-VALUE (MAKE-S) (QUOTE F))))
emacs-cl-eval-interactively((PROGN (DEFSTRUCT S (F 42)) (SLOT-VALUE (MAKE-S) (QUOTE F))))
emacs-cl-newline()
call-interactively(emacs-cl-newline)
Debugger invoked on condition #<UNDEFINED-FUNCTION {12348}>
Available restarts:
0 ABORT
Type "r <n>" or just "<n>" to in invoke a restart,
and "b" to print a backtrace.
0
COMMON-LISP-USER>
COMMON-LISP-USER> (lisp-implementation-type)
"Emacs Common Lisp"
COMMON-LISP-USER> (lisp-implementation-version)
"0.8"
COMMON-LISP-USER>
It works in these implementations:
CLISP 2.41 (2006-10-13) (built on thalassa.lan.informatimago.com [192.168.1.198])
SBCL 1.0.15-gentoo
CMU Common Lisp CVS 19c 19c-release + minimal debian patches (19C)
ECL 0.9g
[···@hubble ~]$ clall "(progn (defstruct s (f 42)) (slot-value (make-s) 'f))"
========================================================================
CLISP 2.41 (2006-10-13) (built on thalassa.lan.informatimago.com [192.168.1.198])
Evaluation of
(PROGN (DEFSTRUCT S (F 42)) (SLOT-VALUE (MAKE-S) 'F))
produced nothing on *STANDARD-OUTPUT*
produced nothing on *ERROR-OUTPUT*
produced no error
produced the following valuess:
--> 42
; loading system definition from
; /usr/share/common-lisp/systems/asdf-binary-locations.asd into
; #<PACKAGE "ASDF0">
; registering #<SYSTEM ASDF-BINARY-LOCATIONS {AEBA471}> as ASDF-BINARY-LOCATIONS
========================================================================
SBCL 1.0.15-gentoo
; in: DEFSTRUCT S
; (DEFSTRUCT S (F 42))
; --> PROGN DEFUN PROGN EVAL-WHEN SB-IMPL::%DEFUN SB-INT:NAMED-LAMBDA FUNCTION
; --> BLOCK LET TRULY-THE SB-KERNEL::%MAKE-INSTANCE-WITH-LAYOUT
; ==>
; (SB-KERNEL::%DELAYED-GET-COMPILER-LAYOUT S)
;
; note: implementation limitation: Non-toplevel DEFSTRUCT constructors are slow.
; in: DEFSTRUCT S
; (DEFSTRUCT S (F 42))
; --> PROGN DEFUN PROGN EVAL-WHEN SB-IMPL::%DEFUN SB-INT:NAMED-LAMBDA FUNCTION
; --> BLOCK LET
; --> (LAMBDA (SB-KERNEL::NEW-VALUE SB-KERNEL:INSTANCE) (LET ((#:ONCE-ONLY-29 SB-KERNEL::NEW-VALUE)) (LET ((#:ONCE-ONLY-30 SB-KERNEL:INSTANCE)) (SB-KERNEL:%INSTANCE-SET (THE S #:ONCE-ONLY-30) 1 (THE T #:ONCE-ONLY-29)))))
; --> LET LET SB-KERNEL:%INSTANCE-SET THE MULTIPLE-VALUE-BIND LET UNLESS IF
; ==>
; (TYPEP #:G129 'S)
;
; caught STYLE-WARNING:
; undefined type: S
; --> PROGN DEFUN PROGN EVAL-WHEN SB-IMPL::%DEFUN SB-INT:NAMED-LAMBDA FUNCTION
; --> BLOCK LET
; ==>
; (TRULY-THE S
; (SB-KERNEL::%MAKE-INSTANCE-WITH-LAYOUT
; (SB-KERNEL::%DELAYED-GET-COMPILER-LAYOUT S)))
;
; caught STYLE-WARNING:
; undefined type: S
; --> PROGN DEFUN PROGN EVAL-WHEN SB-IMPL::%DEFUN SB-INT:NAMED-LAMBDA FUNCTION
; --> BLOCK LET
; --> (LAMBDA (SB-KERNEL::NEW-VALUE SB-KERNEL:INSTANCE) (LET ((#:ONCE-ONLY-29 SB-KERNEL::NEW-VALUE)) (LET ((#:ONCE-ONLY-30 SB-KERNEL:INSTANCE)) (SB-KERNEL:%INSTANCE-SET (THE S #:ONCE-ONLY-30) 1 (THE T #:ONCE-ONLY-29)))))
; --> LET LET SB-KERNEL:%INSTANCE-SET
; ==>
; (THE S #:ONCE-ONLY-30)
;
; caught STYLE-WARNING:
; undefined type: S
;
; caught STYLE-WARNING:
; 2 more uses of undefined type S
;
; caught STYLE-WARNING:
; This type is undefined:
; S
;
; compilation unit finished
; caught 5 STYLE-WARNING conditions
; printed 1 note
Evaluation of
(PROGN (DEFSTRUCT S (F 42)) (SLOT-VALUE (MAKE-S) 'F))
produced nothing on *STANDARD-OUTPUT*
produced nothing on *ERROR-OUTPUT*
produced no error
produced the following valuess:
--> 42
========================================================================
CMU Common Lisp CVS 19c 19c-release + minimal debian patches (19C)
; Converted MAKE-S.
Evaluation of
(PROGN
(DEFSTRUCT S
(F 42))
(SLOT-VALUE (MAKE-S) 'F))
produced nothing on *STANDARD-OUTPUT*
produced nothing on *ERROR-OUTPUT*
produced no error
produced the following valuess:
--> 42
========================================================================
ECL 0.9g
Evaluation of
(PROGN (DEFSTRUCT S (F 42)) (SLOT-VALUE (MAKE-S) 'F))
produced nothing on *STANDARD-OUTPUT*
produced nothing on *ERROR-OUTPUT*
produced no error
produced the following valuess:
--> 42
========================================================================
[···@hubble ~]$
--
__Pascal Bourguignon__ http://www.informatimago.com/
"You can tell the Lisp programmers. They have pockets full of punch
cards with close parentheses on them." --> http://tinyurl.com/8ubpf
Rainer Joswig wrote:
> Hi,
>
> from reading the HyperSpec it seems not to be required that
> SLOT-VALUE works for structures. But most implementations
> are supporting this feature, I'd guess.
>
> Q: is there any CL implementation that does not allow SLOT-VALUE
> to be used with structures?
I tested on Allegro, clisp, Clozure CL, CMUCL, LispWorks and SBCL, and
slot-value on struct instances seems to work in all of them.
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
In article <···············@mid.individual.net>,
Pascal Costanza <··@p-cos.net> wrote:
> Rainer Joswig wrote:
> > Hi,
> >
> > from reading the HyperSpec it seems not to be required that
> > SLOT-VALUE works for structures. But most implementations
> > are supporting this feature, I'd guess.
> >
> > Q: is there any CL implementation that does not allow SLOT-VALUE
> > to be used with structures?
>
> I tested on Allegro, clisp, Clozure CL, CMUCL, LispWorks and SBCL, and
> slot-value on struct instances seems to work in all of them.
Thanks - also to the other Pascal.
It even works on old Genera 8.3 (although the manual says the opposite).
>
>
> Pascal
--
http://lispm.dyndns.org/
Rainer Joswig wrote:
> In article <···············@mid.individual.net>,
> Pascal Costanza <··@p-cos.net> wrote:
>
>> Rainer Joswig wrote:
>>> Hi,
>>>
>>> from reading the HyperSpec it seems not to be required that
>>> SLOT-VALUE works for structures. But most implementations
>>> are supporting this feature, I'd guess.
>>>
>>> Q: is there any CL implementation that does not allow SLOT-VALUE
>>> to be used with structures?
>> I tested on Allegro, clisp, Clozure CL, CMUCL, LispWorks and SBCL, and
>> slot-value on struct instances seems to work in all of them.
>
> Thanks - also to the other Pascal.
>
> It even works on old Genera 8.3 (although the manual says the opposite).
The thing is it's hard to tell whether this works reliably or not. It
may be that under certain optimization settings (or so) slot-value
doesn't work on structs anymore, right?
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
Pascal Costanza wrote:
> The thing is it's hard to tell whether this works reliably or not. It
> may be that under certain optimization settings (or so) slot-value
> doesn't work on structs anymore, right?
[Tangential response: It is curious that a lot of discussion preceded
anyone actually answering the OP's question, paraphrased: Are there any
implementations that _don't_ do this? The apparent answer is "few if
any".]
I can confirm that ACL will work under any optimization environment.
However, while there are efficient and important optimizers for
slot-value on a standard-instance, the execution speed on a
structure-object. Efficiency issues might actually matter to real
applications, especially those that use structures in attempt to regain
a few tens of percent in execution efficiency.
I'd like also to add to Kent's historical summary, that when the
proposal for CLOS was presented to X3J13 by the subcommittee charged
with drafting a specification, there were various opinions how defstruct
should be integrated. I remember that Gregor expressed his personal
preference that defstruct should be simply deprecated entirely, although
the general committee and I think even Gregor understood that the tail
of back compatibility would prevent this from being possible.
defstruct (i.e. structure-object) was developed a long time ago, before
some readers of this list were born. It is defined in a way that
permits compile-time optimization, no reliable redefinition semantics,
and an expected execution speed approximating that of flat array element
access. All implementations of standard-object of which I am aware
represent objects as a duple of a class description and a set of
instance slots. Accessing an instance variable requires two array
indirections, e.g. the equivalent of (aref (aref instance I) J) to refer
to a slot, and the possibility of redefinition prevents heavy
compile-time optimization of the inner index. (Why didn't CLOS specify
an API for class finalization, like Dylan did?)
Steven M. Haflich wrote:
> Pascal Costanza wrote:
>
>> The thing is it's hard to tell whether this works reliably or not. It
>> may be that under certain optimization settings (or so) slot-value
>> doesn't work on structs anymore, right?
>
> [Tangential response: It is curious that a lot of discussion preceded
> anyone actually answering the OP's question, paraphrased: Are there any
> implementations that _don't_ do this? The apparent answer is "few if
> any".]
>
> I can confirm that ACL will work under any optimization environment.
> However, while there are efficient and important optimizers for
> slot-value on a standard-instance, the execution speed on a
> structure-object.
Sucks?
> Why didn't CLOS specify an API for class finalization, like Dylan did?)
You probably mean class _sealing_ here, right?
Because it's hard to combine this with class redefinition capabilities?
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
Pascal Costanza wrote:
> Steven M. Haflich wrote:
>> Pascal Costanza wrote:
>>
>>> The thing is it's hard to tell whether this works reliably or not. It
>>> may be that under certain optimization settings (or so) slot-value
>>> doesn't work on structs anymore, right?
>>
>> [Tangential response: It is curious that a lot of discussion preceded
>> anyone actually answering the OP's question, paraphrased: Are there
>> any implementations that _don't_ do this? The apparent answer is "few
>> if any".]
>>
>> I can confirm that ACL will work under any optimization environment.
>> However, while there are efficient and important optimizers for
>> slot-value on a standard-instance, the execution speed on a
>> structure-object.
>
> Sucks?
Rocks: Cells are a heavy hitter so I tried a lot of different
implementations. One was CLOS, one was faux objects via closures ala a
recent thread, one was faux objects via vectors and hard-coded faux slot
accessors. Oh, and there was the metaclass implementation -- I love it
when slot-value needs to be backdoored. I digress.
What did I learn? Precisely what Mr. Haflich said: CLOS is nicely
optimized by ACL as long as you do not specialize
slot-value-using-class, so cut the AMOP crap in a heavy-hitter. (I would
not be surprised if the same applied to other Lisps, and if it does not
it just means they lack a cool CLOS optimization.)
Even without AMOP interference (ie, just using vanilla CLOS classes)
defstruct kicks CLOS's ass for it, so use defstruct if you can. Because
implementing a Cell as a vector buys you nothing, for reasons obvious
(sadly, only in hindisght) if you have ever used the wrong copy-struct
on a structure instance and had it work.
hth,kt
Kenny <·········@gmail.com> writes:
> Pascal Costanza wrote:
>> Steven M. Haflich wrote:
>>> Pascal Costanza wrote:
>>>
>>>> The thing is it's hard to tell whether this works reliably or
>>>> not. It may be that under certain optimization settings (or so)
>>>> slot-value doesn't work on structs anymore, right?
>>>
>>> [Tangential response: It is curious that a lot of discussion
>>> preceded anyone actually answering the OP's question, paraphrased:
>>> Are there any implementations that _don't_ do this? The apparent
>>> answer is "few if any".]
>>>
>>> I can confirm that ACL will work under any optimization
>>> environment. However, while there are efficient and important
>>> optimizers for slot-value on a standard-instance, the execution
>>> speed on a structure-object.
>>
>> Sucks?
>
> Rocks: Cells are a heavy hitter so I tried a lot of different
> implementations. One was CLOS, one was faux objects via closures ala a
> recent thread, one was faux objects via vectors and hard-coded faux
> slot accessors. Oh, and there was the metaclass implementation -- I
> love it when slot-value needs to be backdoored. I digress.
so, do you routinely use SLOT-VALUE to access structure slots, or do
you not?
it's not a surprise that regular struct slot access (via the accessors
defined by DEFSTRUCT) is very, very fast. SLOT-VALUE is a different
matter.
cheers,
--m
Kenny wrote:
> Pascal Costanza wrote:
>> Steven M. Haflich wrote:
>>> Pascal Costanza wrote:
>>>
>>>> The thing is it's hard to tell whether this works reliably or not.
>>>> It may be that under certain optimization settings (or so)
>>>> slot-value doesn't work on structs anymore, right?
>>>
>>> [Tangential response: It is curious that a lot of discussion
>>> preceded anyone actually answering the OP's question, paraphrased:
>>> Are there any implementations that _don't_ do this? The apparent
>>> answer is "few if any".]
>>>
>>> I can confirm that ACL will work under any optimization environment.
>>> However, while there are efficient and important optimizers for
>>> slot-value on a standard-instance, the execution speed on a
>>> structure-object.
>>
>> Sucks?
>
> Rocks: Cells are a heavy hitter so I tried a lot of different
> implementations. One was CLOS, one was faux objects via closures ala a
> recent thread, one was faux objects via vectors and hard-coded faux slot
> accessors. Oh, and there was the metaclass implementation -- I love it
> when slot-value needs to be backdoored. I digress.
>
> What did I learn? Precisely what Mr. Haflich said: CLOS is nicely
> optimized by ACL as long as you do not specialize
> slot-value-using-class, so cut the AMOP crap in a heavy-hitter. (I would
> not be surprised if the same applied to other Lisps, and if it does not
> it just means they lack a cool CLOS optimization.)
He didn't talk about slot-value-using-class at all, and you probably
just used it incorrectly: There is enough rope in slot-value-using-class
to implement it efficiently as well. (Let me guess: You specialized only
the class parameter, but not the slot definition parameter.)
If I understand Steve's post correctly, he wanted to say that slot-value
on structure instances doesn't perform efficiently. Of course, only he
can clarify this.
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
Pascal Costanza wrote:
> Kenny wrote:
>> Pascal Costanza wrote:
>>> Steven M. Haflich wrote:
>>>> Pascal Costanza wrote:
>>>>
>>>>> The thing is it's hard to tell whether this works reliably or not.
>>>>> It may be that under certain optimization settings (or so)
>>>>> slot-value doesn't work on structs anymore, right?
>>>>
>>>> [Tangential response: It is curious that a lot of discussion
>>>> preceded anyone actually answering the OP's question, paraphrased:
>>>> Are there any implementations that _don't_ do this? The apparent
>>>> answer is "few if any".]
>>>>
>>>> I can confirm that ACL will work under any optimization environment.
>>>> However, while there are efficient and important optimizers for
>>>> slot-value on a standard-instance, the execution speed on a
>>>> structure-object.
>>>
>>> Sucks?
>>
>> Rocks: Cells are a heavy hitter so I tried a lot of different
>> implementations. One was CLOS, one was faux objects via closures ala a
>> recent thread, one was faux objects via vectors and hard-coded faux
>> slot accessors. Oh, and there was the metaclass implementation -- I
>> love it when slot-value needs to be backdoored. I digress.
>>
>> What did I learn? Precisely what Mr. Haflich said: CLOS is nicely
>> optimized by ACL as long as you do not specialize
>> slot-value-using-class, so cut the AMOP crap in a heavy-hitter. (I
>> would not be surprised if the same applied to other Lisps, and if it
>> does not it just means they lack a cool CLOS optimization.)
>
> He didn't talk about slot-value-using-class at all....
And I did not say he did, nor did I say I was limiting my answer to
precisely what was asked vs. branching off into everything I learned
while trying to optimize Cells for any possible benefit that might have
to folks trying to go faster than CLOS which is my idea of being helpful
vs literally responding only to the question at hand like the engineer
on the ground to the manager in the balloon.
, and you probably
> just used it incorrectly:
Silly wabbit! How could I do that? I specialized as needed, no more and
no less. This is programming, we say what we mean and mean what we say,
or Things Fall Apart.
> There is enough rope in slot-value-using-class
> to implement it efficiently as well.
I am just telling you what I learned from Franz tech support when I
broke their SVUC.
> (Let me guess: You specialized only
> the class parameter, but not the slot definition parameter.)
But then how would I code up SVUC sensibly given my classes had a mix of
Cell-specific slots and standard slots?
Only in one of the half dozen methods, when I wanted to safeguard
against using a non-Cellular slot as if it were cellular. But I did that
by specializing on a Cell as the first value. But it would be
interesting to see if losing the airbag (or specializing on the standard
slot class) would avoid the hit. I do not recall what Franz said, but I
think it would not help -- the optimization was pretty much to lose SVUC
as long as the client (me) was not beating on it. Quoth me not.
kt
Kenny wrote:
>> (Let me guess: You specialized only the class parameter, but not the
>> slot definition parameter.)
>
> But then how would I code up SVUC sensibly given my classes had a mix of
> Cell-specific slots and standard slots?
(defclass cell-effective-slot-definition
(standard-effective-slot-definition)
())
(defmethod slot-value-using-class :after
((class cell-class) object (slot cell-effective-slot-defintion))
... trigger updates of other slots ...)
...and make sure that effective-slot-definition-class returns
(find-class 'cell-effective-slot-definition) only for those slots where
you actually need that behavior.
A nice additional property is that this is stable wrt class
redefinition, while I have doubts that you can remove cell-specific
behavior for slots in a straightforward way once they got it in a pure
macro solution.
That's actually a good rule of thumb: Use macros for purely static
metaprogramming, and the CLOS MOP (or similar dynamic means) for
metaprogramming that has to affect dynamic properties of a program.
Combining the two approaches is actually quite powerful, if you know how
to distribute the "responsibilities" between the static and dynamic
parts well...
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
Pascal Costanza wrote:
> Kenny wrote:
>
>>> (Let me guess: You specialized only the class parameter, but not the
>>> slot definition parameter.)
>>
>> But then how would I code up SVUC sensibly given my classes had a mix
>> of Cell-specific slots and standard slots?
>
> (defclass cell-effective-slot-definition
> (standard-effective-slot-definition)
> ())
>
> (defmethod slot-value-using-class :after
> ((class cell-class) object (slot cell-effective-slot-defintion))
> ... trigger updates of other slots ...)
>
> ...and make sure that effective-slot-definition-class returns
> (find-class 'cell-effective-slot-definition) only for those slots where
> you actually need that behavior.
Sorry for wasting your time: there was an implicit "If your guess were
correct,..." in the front of that. ie, Your guess was wrong, and of
course I used custom slot definitions if only because of the extra
initialization arguments Cells requires. But then you do not know about
those, either, just as you did not know Cells supported slots not
mediated by Cells in any way.
The moral of the story involves guessing less and asking more.
kt
Kenny wrote:
> Pascal Costanza wrote:
>> Kenny wrote:
>>
>>>> (Let me guess: You specialized only the class parameter, but not the
>>>> slot definition parameter.)
>>>
>>> But then how would I code up SVUC sensibly given my classes had a mix
>>> of Cell-specific slots and standard slots?
>>
>> (defclass cell-effective-slot-definition
>> (standard-effective-slot-definition)
>> ())
>>
>> (defmethod slot-value-using-class :after
>> ((class cell-class) object (slot cell-effective-slot-defintion))
>> ... trigger updates of other slots ...)
>>
>> ...and make sure that effective-slot-definition-class returns
>> (find-class 'cell-effective-slot-definition) only for those slots
>> where you actually need that behavior.
>
> Sorry for wasting your time: there was an implicit "If your guess were
> correct,..." in the front of that. ie, Your guess was wrong, and of
> course I used custom slot definitions if only because of the extra
> initialization arguments Cells requires. But then you do not know about
> those, either, just as you did not know Cells supported slots not
> mediated by Cells in any way.
The I don't understand where you get a performance hit...
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
Pascal Costanza wrote:
> Kenny wrote:
>> Pascal Costanza wrote:
>>> Kenny wrote:
>>>
>>>>> (Let me guess: You specialized only the class parameter, but not
>>>>> the slot definition parameter.)
>>>>
>>>> But then how would I code up SVUC sensibly given my classes had a
>>>> mix of Cell-specific slots and standard slots?
>>>
>>> (defclass cell-effective-slot-definition
>>> (standard-effective-slot-definition)
>>> ())
>>>
>>> (defmethod slot-value-using-class :after
>>> ((class cell-class) object (slot cell-effective-slot-defintion))
>>> ... trigger updates of other slots ...)
>>>
>>> ...and make sure that effective-slot-definition-class returns
>>> (find-class 'cell-effective-slot-definition) only for those slots
>>> where you actually need that behavior.
>>
>> Sorry for wasting your time: there was an implicit "If your guess were
>> correct,..." in the front of that. ie, Your guess was wrong, and of
>> course I used custom slot definitions if only because of the extra
>> initialization arguments Cells requires. But then you do not know
>> about those, either, just as you did not know Cells supported slots
>> not mediated by Cells in any way.
>
> The I don't understand where you get a performance hit...
You would have to ask Franz. The idea is probably, golly, supporting all
the options implicit in the svuc gf specializations sher is expensive,
what if we silently optimized it away (as long as they do not provide
methods for the GF, in which case we have no way of knowing what they
are doing in their methods so we still have to go thru svuc)? Cool!
I recall a pause during loadiing of my code during which I guessed ACL
was loading up the real slot-value (the one that calls svuc) and the
whole svuc code and backing out the optimizations. Might have been my
imagination -- return to first sentence.
The better question is why you said slot-value on defstructs sucked
since it is just an array access, that one had me stumped.
kt
Kenny wrote:
> Pascal Costanza wrote:
>> Kenny wrote:
>>> Pascal Costanza wrote:
>>>> Kenny wrote:
>>>>
>>>>>> (Let me guess: You specialized only the class parameter, but not
>>>>>> the slot definition parameter.)
>>>>>
>>>>> But then how would I code up SVUC sensibly given my classes had a
>>>>> mix of Cell-specific slots and standard slots?
>>>>
>>>> (defclass cell-effective-slot-definition
>>>> (standard-effective-slot-definition)
>>>> ())
>>>>
>>>> (defmethod slot-value-using-class :after
>>>> ((class cell-class) object (slot cell-effective-slot-defintion))
>>>> ... trigger updates of other slots ...)
>>>>
>>>> ...and make sure that effective-slot-definition-class returns
>>>> (find-class 'cell-effective-slot-definition) only for those slots
>>>> where you actually need that behavior.
>>>
>>> Sorry for wasting your time: there was an implicit "If your guess
>>> were correct,..." in the front of that. ie, Your guess was wrong, and
>>> of course I used custom slot definitions if only because of the extra
>>> initialization arguments Cells requires. But then you do not know
>>> about those, either, just as you did not know Cells supported slots
>>> not mediated by Cells in any way.
>>
>> The I don't understand where you get a performance hit...
>
> You would have to ask Franz. The idea is probably, golly, supporting all
> the options implicit in the svuc gf specializations sher is expensive,
> what if we silently optimized it away (as long as they do not provide
> methods for the GF, in which case we have no way of knowing what they
> are doing in their methods so we still have to go thru svuc)? Cool!
>
> I recall a pause during loadiing of my code during which I guessed ACL
> was loading up the real slot-value (the one that calls svuc) and the
> whole svuc code and backing out the optimizations. Might have been my
> imagination -- return to first sentence.
I don't know about Franz's implementation, but I think it should be
possible to get good speed out of s-v-u-c if it's specialized
reasonably. IIRC, SBCL has made some good attempts at that.
> The better question is why you said slot-value on defstructs sucked
> since it is just an array access, that one had me stumped.
I didn't say this, I asked what Steve actually meant. (It was a genuine
question.)
I can imagine that optimizations for slot-value are restricted to CLOS,
because it's not supposed to be used for structs. Could be an accidental
circumstance (like with s-v-u-c). Yes, there is no principle reason why
it shouldn't be fast (it should actually be easier than for CLOS).
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
>
>> The better question is why you said slot-value on defstructs sucked
>> since it is just an array access, that one had me stumped.
>
> I didn't say this, I asked what Steve actually meant. (It was a genuine
> question.)
>
> I can imagine that optimizations for slot-value are restricted to CLOS,
> because it's not supposed to be used for structs. Could be an accidental
> circumstance (like with s-v-u-c). Yes, there is no principle reason why
> it shouldn't be fast (it should actually be easier than for CLOS).
>
struct accessors can be inlined to array access.
slot-value in general can't since CLOS allows attributes to be added at
runtime so you get one level of indirection.
I can't see why the compiler could't inline slot-value for struc's however.
--------------
John Thingstad
"John Thingstad" <·······@online.no> writes:
> struct accessors can be inlined to array access. slot-value in
> general can't since CLOS allows attributes to be added at runtime so
> you get one level of indirection. I can't see why the compiler
> could't inline slot-value for struc's however.
I think that one level of indirection is possible for the first
generation of a class layout. This might provide a nice speed boost
for delivered applications where redefinition is not likely.
Imagine that we have a class with two slots. We could lay out an
instance created from the initial class definition in a vector like
so:
0: class pointer
1: generation count = 0
2: slot0
3: slot1
If generation count == 0, then slot-value uses the data in positions 2
and 3. Otherwise slot-value indirects. When the class gets
redefined, we can have an instance layout like so:
0: class pointer
1: generation count = 1
2: points to vector of slot data
3: unused, set to NIL
-russ
Russell McManus wrote:
> "John Thingstad" <·······@online.no> writes:
>
>> struct accessors can be inlined to array access. slot-value in
>> general can't since CLOS allows attributes to be added at runtime so
>> you get one level of indirection. I can't see why the compiler
>> could't inline slot-value for struc's however.
>
> I think that one level of indirection is possible for the first
> generation of a class layout. This might provide a nice speed boost
> for delivered applications where redefinition is not likely.
>
> Imagine that we have a class with two slots. We could lay out an
> instance created from the initial class definition in a vector like
> so:
>
> 0: class pointer
> 1: generation count = 0
> 2: slot0
> 3: slot1
>
> If generation count == 0, then slot-value uses the data in positions 2
> and 3. Otherwise slot-value indirects. When the class gets
> redefined, we can have an instance layout like so:
>
> 0: class pointer
> 1: generation count = 1
> 2: points to vector of slot data
> 3: unused, set to NIL
It can also be quite efficient in later generations. I think Christophe
Rhodes has a nice description how this is done in PCL, but I don't
recall where to find that.
Pascal
--
My website: http://p-cos.net
Common Lisp Document Repository: http://cdr.eurolisp.org
Closer to MOP & ContextL: http://common-lisp.net/project/closer/
Rainer Joswig <······@lisp.de> writes:
> Hi,
>
> from reading the HyperSpec it seems not to be required that
> SLOT-VALUE works for structures. But most implementations
> are supporting this feature, I'd guess.
>
> Q: is there any CL implementation that does not allow SLOT-VALUE
> to be used with structures?
OK. If you use the :TYPE option to defstruct, then you can end up with
structures for which SLOT-VALUE will not work.
It seems that you will be OK if you stay away from structures with
explicitly defined implementation types, though.
--
Thomas A. Russ, USC/Information Sciences Institute