On Jul 13, 2005, at 1:12 PM, Larry Wall wrote:

If class Dog does role Bark and also does role Wag, then passing a
Dog to

    multi (Bark $x)
    multi (Wag $x)

should result in ambiguity.

My understanding is that a Role is an abstract (i.e. cannot be instantiated) blob of methods and, possibly, data. The purpose of a Role is to paste it into a class--in other words, a Role is a not a type, it is a part of a type. Assuming that that understanding is correct, then I would expect the above multi declarations to be a compile time error: 'multi (Wag $x)' means "expect some data, call it $x, which will be of type Wag"...but Wag isn't a type, it's a partial type.

I would require that declaration to be written as one of the following:

multi (Dog does Bark $x) # Dog is an actual type that can be instantiated
    multi (Animal does Bark $x)    # Animal is an abstract base class
multi (Object does Bark $x) # Object (or whatever the name is) is the root of the entire class/type hierarchy

I could see stretching a point and allowing the last one to be rewritten as:

    multi (does Wag $x)    # Still references root type, but implicitly

The point of this is to force the programmer to give a reasonable constraint...when they expect something that Wags, does it need to be a Dog, or will any Animal that can Wag be sufficient? Or are they really looking for absolutely anything that is capable of Wagging?


Doing it this way would (I think) be both more intuitive and would resolve a lot of the ambiguity that was discussed farther on.


    multi (does Bark $x)
multi (Dog does Bark $x) # Dog is more specific than "any data type"

---new example

    multi (Tree does Bark $x)
multi (Dog does Bark $x) # Equally specialized classes in separate parts of the hierarchy. If passed an "Object does Bark" param, this should be an error.

---new example

multi (Labrador does Bark $x) # Labrador is a subclass of Dog and therefore more specific if passed a Labrador param multi (Dog does Bark $x) # This catches any other 'Dog' params multi (does Bark $x) # This catches anything else that Barks, including 'Dingo is Dog does not Bark'


The interesting question is whether N should
be 0 or 1 (or possibly epsilon).  If we have

    multi (Bark $x)
    multi (Dog $x)

arguably Dog is more specialized than Bark,
[...]
The problem with N == epsilon is in visualizing how Dog is more constrained
than Bark.

Assuming that the declaration of Dog is 'class Dog does Bark', then yes, I think Dog should be considered more specialized than Bark-- lots of things might Bark, but only a Dog will bark in precisely this way. Or, to put it a different way, a 'Dog' class has a certain specificity and a 'Bark' Role has a certain specificity: the combination of the two produces something more specific than either. (And, of course, 'Dog does Bark does Wag' (or 'Dog does Bark&Wag' if you prefer) is yet more specific.)

--Dks



Reply via email to