[Openmcl-devel] make-method-lambda ?

Pascal Costanza pc at p-cos.net
Wed Sep 10 13:58:02 UTC 2008


On 10 Sep 2008, at 10:41, james anderson wrote:

> On 2008-09-09, at 13:11 , Pascal Costanza wrote:
>
>> You have to keep track of that anyway. The semantics of define-
>> manipulated-method is sufficiently different from (standard)  
>> defmethod
>> that it warrants using different names to make that distinction
>> explicit.
>
> my experience has been, that this distinction is academic and can be
> less useful in practice than on paper.
> circumstances vary.

Don't call me academic! ;)

>> The idea of make-method-lambda is that you can use methods
>> defined using defmethod interchangeably with different semantics in
>> different contexts/generic functions, but it's actually very unlikely
>> that a change of semantics (the fact whether the arguments are
>> manipulated or not in your example) will _not_ have an effect on the
>> method body.
>
> i am concerned with a case where there is to be no effect. that's the
> point of it.

I find it hard to imagine that you need such strong weapons then.

Wouldn't a user-defined method combination that modifies arguments in  
an "around around" method enforced by the generic function be simpler  
then in such a case (and more efficient)?

>> The advantage is that your code is more explicit. I think that makes
>> it easier to keep track of things, not harder.
>
> what you suggest is the equivalent of "unrolling" optimization. with
> the attendant benefits and drawbacks. under many circumstances the
> resulting computation is equivalent, but as soon as let-binding and
> re-computation become concerns, the benefits fade.
>
> a thought experiment. method combination objects are in a similar
> "neglected stepchild" position with respect to ensure-generic-
> function as the generic function argument with respect to make-method-
> lambda. it is conceivable to argue, that one could improve the
> situation by implementing compute-effective-method as an inline macro-
> expansion for define-generic-function. that this does not work for
> various reasons, and would be a generally bad idea, suggests the
> drawbacks inherent in inline expansion for make-method-lambda and why
> it runs counter to the mop's paradigm.

You're arguing from the point of view of how semantic changes are  
achieved. I'm arguing from the point of view what the programmer has  
to specify to get those semantic changes.

In that regard, method combinations are actually a good example: It is  
possible in user-defined method combinations to have unqualified  
methods play a different role than the usual role of primary methods  
in standard method combination. However, all the predefined method  
combinations require the qualifier to name the method combination in  
use. So, for example, the method combination 'progn requires the use  
of the 'progn qualifier in a defmethod form, etc. Apparently, the CLOS  
designers thought it'd be beneficial to be explicit (and I think it's  
a good idea to follow that example in your own method combinations).

Likewise, all defining forms in CLOS except defmethod require explicit  
mention of the respective metaclass - so :metaclass for  
defclass, :generic-function-class for defgeneric. Indeed, Kiczales  
admitted that it was a mistake not to have specified a :method-class  
option in defmethod forms - the :method-class option in defgeneric is  
only meant as a default value, not as the only acceptable value for  
methods being added to a generic function.

Assuming that there were a :method-class option in defmethod, you can  
then see that there is no real difference anymore between providing a  
method on make-method-lambda and providing one's own define-xyz-method  
form.

I really think that the additional benefit of being able to use  
defmethod forms unchanged is really, really minor, especially when  
considering the fact that a change of the :method-class option in  
defgeneric requires a recompilation of _all_ involved defmethod forms.  
(As stated in our paper, there is no corresponding runtime protocol  
for having an effect on method bodies here.)

And that's the essence of my argument: The CLOS MOP is a runtime  
metaobject protocol, and make-method-lambda is the only exception that  
stands out. Make-method-lambda is redundant, because we already have a  
very stable and mature compile-time metaobject protocol - aka Common  
Lisp's macro system - with the added benefit that it's actually really  
portable.


Pascal

-- 
Pascal Costanza, mailto:pc at p-cos.net, http://p-cos.net
Vrije Universiteit Brussel, Programming Technology Lab
Pleinlaan 2, B-1050 Brussel, Belgium









More information about the Openmcl-devel mailing list