On Sat, 30 Jul 2005, Adam P. Jenkins wrote:

> Ara.T.Howard wrote:
>> On Fri, 29 Jul 2005, Jim Weirich wrote:
>> 
>>>> did you run this?  this is most defintely __not__ the diamond problem - 
>>>> it
>>>> is strictly a tree:
>>> 
>>> 
>>>> From my point of view, it looks like a diamond include structure, i.e.
>>> 
>>> 
>>>     A
>>>    / \
>>>   B   C
>>>    \ /
>>>     D
>>> 
>>> Ruby does linearizes the method resolution order to D,C,B,A.
>> 
>> 
>> right - we are saying the same thing - the diamond is reduced to a line - 
>> ergo
>> no 'diamond' problem - it's avoided by requiring the programmer to order 
>> the
>> line via 'include'.
>
> By your logic, C++ and Python don't have the diamond problem either. Both of
> those languages have well defined ways in which the method to call is
> chosen, which have to do with the order in which the programmer writes
> things.  So from the compiler's point of view, there is never a diamond
> problem, unless you had a language specification which didn't define any
> rules for resolving the issue.  The "diamond problem" is a problem for
> humans, who may not always remember, or take into account, the language's
> rules for choosing which method to call, so in that sense Ruby's module
> include feature introduces exactly the same "diamond problem" that multiple
> inheritence introduces into other languages.

all true - but only for methods.  the thing with inheritence is that state
(instance vars) also get inherited.  with ruby writing

   module M
     def foobar
       @foobar || = 42
     end
   end
   module N
     def foobar_foobar
       @foobar || = 42
       [@foobar, @foobar]
     end
   end
   class A
     include M
     include N
   end
   class B
     include M
     include N
   end

   p A::new.foobar
   p A::new.foobar_foobar
   p B::new.foobar
   p B::new.foobar_foobar

results in the A object and the B object having exactly one copy of @foobar in
them.  if A and B inherited from, rather than mixed-in, M and N then the
'problem' is what to do with @foobar.  ruby could, as c++ has done, add
something like a virtual keyword to allow the programmer to prevent having two
copies of @foobar, it could merge them, who knows.  it would, however, be a
'problem' that we don't currently have - and that c++ and python do.  another
issue is

   class A
     def foobar
       42
     end
   end

   class B
     def foobar
       'forty-two'
     end
   end

   class C < A, B
     def foobar
       super  # what does this do?
     end
   end

   class D < C
     def foobar
       super
     end
     def initialize
       class << self
         def foobar
           super  # what does this do?
         end
       end
     end
   end

   module M
     def foobar
       super
     end
   end

   class E < D
     extend M # what does this do when E#foobar is called?
   end

it's not that these things are not solvable - just that they are hard.  c--
solved some of the above by having a complex syntax for calling specific
'supers'.  it took compiler writers __years__ to follow the c++ spec and
multiple inheritence was one of the more difficult things to do (apparently).
the handling of it is non-trivial for the compiler writer.

so now we do have a simple kind of 'diamond inheritence' but no 'diamond
problem' in the ruby runtime since the ordering of module inclusion, as
written by the programmer, makes totally unambiguous the search path of method
calls.

cheers.

-a
-- 
===============================================================================
| email :: ara [dot] t [dot] howard [at] noaa [dot] gov
| phone :: 303.497.6469
| My religion is very simple.  My religion is kindness.
| --Tenzin Gyatso
===============================================================================