> http://en.wikipedia.org/wiki/Diamond_problem
C++ solved this problem a long time ago. You can either use virtual inheritance or say explicitly if you want to use B's or C's method (using the class identifiers from the wikipedia article). And your assertion that interfaces effectively accomplish the same thing as multiple inheritance is just wrong, you can't do mixins with Java interfaces. So, the way I see it, Java didn't actually solve any problem (like C++ did with virtual inheritance), but it just disallowed multiple inheritance even in cases where the diamond "problem" doesn't even arise.
Posted Apr 5, 2011 20:38 UTC (Tue) by cmccabe (guest, #60281)
[Link]
As the Gang of Four book says, you should "favor 'object composition' over 'class inheritance'." So rather than creating mixins, you should usually create objects that are comprised of several smaller objects which operate independently.
There are a lot of reasons for this. The first and most obvious reason is that it makes unit testing a lot easier. If I have a class which inherits from 3 other classes, I can't test that class without also testing the three base classes. I may not even be able to construct an instance of that class without providing a lot of irrelevant inputs-- file descriptors to open, memory to allocate, and so forth. On the other hand, it's easy to create an instance of a component and test just that component.
You can get around some of these problems by constructing "mock ups" of some of your class components. You see this a lot in Java code. But it's difficult, and even when executed successfully, it bloats the code.
Creating elaborate and deep inheritance hierarchies increases compile time and the coupling between components. The former chews up machine cycles when compiling (at least if you're using C++). The latter chews up human time when trying to maintain the code, no matter what language you're using.
Posted Apr 5, 2011 22:43 UTC (Tue) by HelloWorld (guest, #56129)
[Link]
Firstly, this is a general statement about inheritance and has little to do specifically with multiple inheritance. Secondly, if we assume the GoF to be right, then Java did it just as wrongly as C++, as it still allows inheritance.
GCC 4.6.0 released
Posted Apr 5, 2011 23:24 UTC (Tue) by cmccabe (guest, #60281)
[Link]
My main point is that using inheritance for code reuse is bad.
Using inheritance to implement runtime polymorphism is still ok.
So Java interface classes and C++ abstract base classes are ok in my book. Mixins are bad, in my opinion.
I do like the way Golang handles runtime polymorphism more than the way C++ or Java do it, but you can only do it that way if you're using Go. :)
GCC 4.6.0 released
Posted Apr 7, 2011 16:42 UTC (Thu) by daglwn (subscriber, #65432)
[Link]
Mixins do not have to implement anything. Again, you're artificially restricting what's possible. It's sometimes convenient to use mixins to convey relationships among types. I have a mother and a father. My mother has a mother and a father. So does my father. That means my maternal-side cousin and I have grandparents in common and my paternal-side cousin and I also have grandparents in common, but a different set.
In more concrete terms, an add expression is a binary operator. So is a subtract expression. Both are also associative, but only one is commutative. That's a useful thing to express in class hierarchies and using mixins is a great way to do it.
GCC 4.6.0 released
Posted Apr 8, 2011 17:57 UTC (Fri) by cmccabe (guest, #60281)
[Link]
from Wikipedia:
> In object-oriented programming languages, a mixin is a class that provides
> a certain functionality to be inherited by a subclass, while not meant for
> instantiation (the generation of objects of that class). Inheriting from a
> mixin is not a form of specialization but is rather a means of collecting
> functionality.
So it's not about relationships between types. It is about code reuse.
Bruce Eckel suggests a way of implementing mixins in C++ using templates:
Posted Apr 8, 2011 18:35 UTC (Fri) by daglwn (subscriber, #65432)
[Link]
I've used CRTP as well and find it useful. I also find mixins as relationship useful. I my mind, inheritance is about relationships. For functionality, I would agree with GoF and you that composition is generally a better path. I very rarely use private inheritance. I honestly can't think of a situation where I've found it absolutely necessary.
But in any case, I think the discussion leads us to a place where general MI is useful, even with the pitfalls. Pointers in C have a similar usefulness/pitfall tradeoff. I like the fact the C++ is flexible like this. I wish it were more flexible than it is! :)
GCC 4.6.0 released
Posted Apr 11, 2011 0:30 UTC (Mon) by cmccabe (guest, #60281)
[Link]
Well, as I said before, I think being able to inherit from multiple (fully) abstract base classes is useful. I have never found a good use for inheriting from multiple non-abstract base classes. I guess we'll have to agree to disagree.
Anyway, language design is an endless process. It really comes down to who what languages are most successful in the marketplace, and in the open source world. My philosophy is to use the right tool for the job.