> -----Original Message-----
> From: Larry Wall [mailto:[EMAIL PROTECTED]
>
> On Fri, Apr 23, 2004 at 02:07:16PM -0400, Austin Hastings wrote:
> : I guess I'm more strongly attached to the sigil than I
> realized. IMO, if you
> : have
> :
> : $obj handles 'a';
> :
> : and put an arrayref in $obj, then you get what's coming:
> iteration. But if
> : you have
> :
> : @obj handles 'a';
> :
> : then you know it's an array, or array subtype, and delegate
> array-things to
> : it.
> :
> : So I prefer cases 1:s, 1:n, and a:a instead of 1:s, 1:a, and a:n.
>
> But a delegating attribute is not an alias for its delegatee, or if it is,
> should maybe not be thought of as one. The question is, if you've gone
> and delegated to another object, should this class be mucking around with
> the innards of the array object as if it owned it? I don't think so.
> I think it's better to have the reference in a scalar variable to remind
> you of that it's a different object. On the other hand, the list of
> handlers *is* a valid concern for this class, and it shouldn't have to
> go poking down through a reference to get at that list. It has a valid
> use for the @ sigil.
Aha! A light comes on:
Delegation is not the same as subordination.
The C<handles> delegation syntax declares "formal"
delegation, meaning that the handler is treated as a
separate object. Thus, by default delegate objects
are stored in scalar references.
However, you may delegate to many objects by using
the @handler or %handler syntaxes.
That's an explanation/ideology I can sink my teeth into.
Can I declare a const reference and have it optimized away?
class Queue {
has @:elements;
has $:array_delegate
handles <push pop int>
= \@:elements
is const;
}
>
> : > : Also, it's not clear:
> : > :
> : > : "first one that succeeds"
> : > :
> : > : Does that mean "First one for which a matching
> : > : method exists" or does it mean "First one for which
> : > : a method exists that does not C<fail> or return
> : > : undef or some other badness"?
> : >
> : > The latter is the intent.
> :
> : Then array handling is doing some sort of .+method
> : dispatch instead of "plain old dispatch", no?
>
> No, it's plain old, I expect.
>
> : I think this should be made explicit. At first glance,
> : I'd hate to lose C<return undef;> or C<return FALSE;>
> : as an option just because than means "keep searching for
> : handlers".
> :
> : Can you tell us why the initial spec calls for continuing
> : search?
>
> It doesn't. The question in question had an "or", which
> seem in your thinking to have mutated into an "and". The
> "badness" in the question in question is provided by "next
> METHOD", not by returning false or undef. So if a method
> knows it can handle something, all it does is return the
> value, whatever that is.
Okay.
So one way to fail would be a subtype violation:
class Row {
has @:flavors
handles <print_row>;
}
type OddRow ::= Row where $:row_num mod 2 == 1;
type EvenRow ::= Row where $:row_num mod 2 == 0;
$even_row = new Row(row_num => 0);
$odd_row = new Row(row_num => 1);
@:flavors = (
$even_row,
$odd_row
);
$row.print_row;
Right? (I know, this could be done with a multimethod.)
So what are the ways to fail?
-> Subtype incompatibility, as above
-> Invocation signature: Does the @:handlers list become a wierd sort of
tunable multimethod dispatch?
-> C<fail> keyword?
-> C<next METHOD> obviously
-> Others?
=Austin