What you have when a class has more than one direct superclass. Some OO languages have MultipleInheritance (for instance: CeePlusPlus, CommonLisp, PythonLanguage, PerlLanguage); some don't (for instance: SmalltalkLanguage, ModulaThree, JavaLanguage). Java does have a sort of half-way house called "interfaces", providing multiple inheritance of interface but not of implementation. (When I switched from C++ to Java I got blesses on my fingas.)
Some people like MultipleInheritance, some don't. See MultipleInheritanceIsNotEvil, and maybe also MultipleInheritanceInSmalltalk.
Not to be confused with MultipleDispatch, which is what happens when method dispatch looks at the (dynamic) type of more than one object. (And which people disagree on just as much as they do about MultipleInheritance.)
Surely no one thinks MultipleDispatch is evil?
The classic first complaint about MI is inherited method clash. And just why can't people establish that inherited implementation clashes are illegal, and otherwise allow MI? That would have the side effect of preventing diamond-shaped hierarchies for all but the most abstract of classes. Essentially, it makes the practical issues disappear. This still leaves the damage you can cause with TaxoMania, but that is a BadProgrammer problem, not a BadFeature? problem. -- IanKjos
There is no method clash. In CommonLisp, for example, each class has a precedence list, which is used to determine all applicable methods at time of dispatch. This problem is a myth, and only exists in some (poorly, in my opinion) designed languages. --AlainPicard
Please don't forget EiffelLanguage. It does MultipleInheritance right.
MultipleInheritance of implementation allows for MixIns.
Some of us RelationalWeenies see "sets" when we see multiple inheritance. Multiple inheritance is an oxymoron IMO because if you have multiple parents, then it is not really a true hierarchy any more. It is my belief that LimitsOfHierarchies will eventually lead to sets as real-world complexity creeps into a project/system, which will lead to relational-like technology. Perhaps this is an AllRoadsLeadToRome sin, but that is how I see it. Hierarchies are easy to relate to (initially), but don't scale well over time (changes) or project size increases. -t
Yes, classes are sets of functions. How is that comparable to relational where there are sets of data?
Classes are sets of objects, not sets of functions. MultipleInheritance reflects the fact that sets may intersect, and is often an ugly kludge.
Why must it be a hierarchy? Why not a simple directed graph?
It can be a graph. With multiple inheritance, it is a "multiarchy" instead of a hierarchy. The issue that must be resolved, however, is the order in which conflicts are resolved. If a given class inherits from both classA and classB, and both classA and classB define someMethod, then the order determines whether classA.someMethod or classB.someMethod is actually selected. Similarly, if either method includes a call to "super", or its equivalent, then the order determines which ancestor's method is selected. The "conflict" isn't a problem, per se. The multiple-inheritance mechanism simply needs to provide a mechanism for resolving the choice.
See also: CallingaSpadeaSpade