> I do like this approach to composition/delegation, but it requires
> automatically adding a lot of methods to the delegator, i.e. Unicycle in
> this example, from all of its components, which feels kind of nasty and
> dangerous, especially since we allow dynamic addition of methods
> after-the-fact. In other words, you might add a method to Wheel, Frame or
> Seat at any time, which would presumably then also apply to Unicycle
> objects, potentially with unexpected consequences. It would be nice if the
> delegation was more limited than that. Go doesn't have this problem since
> you can't dynamically add methods – everything is known at compile time.
>
Yea, it's this kind of thing that makes it tricky in Julia. The obvious
problem is that you add a method (say cushiness to Frame) which makes
dispatch ambiguous. One could add higher-level dispatch rules, but that's
likely to add a lot of complexity.
On Thursday, October 22, 2015 at 7:03:43 AM UTC-6, Abe Schneider wrote:
>
> I think this is generally in-line with what I've been advocating for, and
> not that different from Scala's mix-ins:
>
> trait Wheel {
> // ...
> }
>
> trait Frame {
> // ...
> }
>
> class Unicycle extends trait Wheel, Frame {
> // ...
> }
>
> is essentially doing the same thing (i.e. copying the member variables and
> methods over).
>
>
I'm not familiar with Scala, so sorry if I'm telling you something you
know, but in go the member variables and methods are not copied over. The
Unicycle struct in go does not itself have those fields, the fields of the
struct do. In other words, defining
type Unicycle struct {
Frame
Wheel
Seat
}
Is exactly like declaring
type Unicycle struct {
Frame Frame
Wheel Wheel
Seat Seat
}
except that in the former case one can call unicycle.Cushiness() , and in
the latter one must call unicycle.Seat.Cushiness(). In particular, if you
swap out one Frame in the unicycle for a different Frame, the field values
change (the methods won't, since methods are with a type).