From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.5-pre1 (2020-06-20) on ip-172-31-74-118.ec2.internal X-Spam-Level: X-Spam-Status: No, score=-1.9 required=3.0 tests=BAYES_00 autolearn=ham autolearn_force=no version=3.4.5-pre1 Date: 15 Sep 92 14:08:40 GMT From: haven.umd.edu!darwin.sura.net!Sirius.dfn.de!Urmel.Informatik.RWTH-Aachen. DE!vivaldi!pk@ames.arc.nasa.gov (Peter Klein) Subject: Re: MI - clutching at straws Message-ID: <1992Sep15.140840.3405@Urmel.Informatik.RWTH-Aachen.DE> List-Id: In article 92Sep14151942@Dr_No.mitre.org, eachus@Dr_No.mitre.org (Robert I. Eac hus) writes: >In article <1992Sep9.142434.3940@Urmel.Informatik.RWTH-Aachen.DE> pk@rwthi3.in formatik.rwth-aachen.de (Peter Klein) writes: > > > Unfortunately, your arguments don't hold in my example, where several > > extensions of the same base type are combined. The resulting type is > > essentially the base type augmented by an arbitrary subset of the possible > > extensions. The problems you mentioned cannot arise in this context. > > Furthermore, it is pretty awkward to simulate such behaviour without MI. > > But it is exactly that case...the (base) type is extended with lists >and trees, and then these extensions are combined. (It is hard not to >use nasty words to relieve frustration at this point, but I know that >this is a hard enough to understand mechanisms like type extension and >inheritance, and the subtile differences in mechanisms discussed here >tend to rapidly convert any brain into jelly, but bear with me.) > Well, either you didn't understand my example or I didn't understand yours :). Here's my understanding of what you said: You have some base type, say X. Now you make up lists and trees which *contain* entries of type X. Right? But then, neither the list nor the tree class are subtypes of X. They are containers with no common base class and therefore cannot be "merged" in my proposal. The other possibility would be that your base class is a container class like lists, and then you make subtypes for trees and sets. In this case, it is first of all doubtful that inheritance should be used at all to design this (since the inheritance is completely on the implementation part; this is more likely a simple import). Anyway, if you insist to do so, you could make a class then which is both a set and a tree. But who would want to do so? > Part of the problem is semantic. I think Tucker will be glad to >explain to you how Ada implements multiple inheritance, while most of >us use MI to mean something other than generic instantiation, but >Tucker does have a point. The Ada 9X mechanisms are safer and more >general than those offered by most instances of MI, but it does >require more thinking up front by the designer of a mix-in. > > > Not true. Inheritance is the more powerful feature. Dynamical binding canno t > > be done with genericity; you'll never get true polymorphism without > > inheritance. But I don't think this is the question. Genericity and > > inheritance both have their uses, and most of the time the design makes > > clear which of them is appropriate in a given situation. If you think that > > inheritance is not *really* needed, I can accept that. But my original > > question was: What do I loose when I have SI only? > > I assume that you left a word out above, since in my post I did >say that inheritance is sometimes necessary, it is union style >multiple inheritance that is unnecessary in Ada or any other language >with sufficiently powerful generic capabilities. > Hmm, isn't this exactly what I said? I mean, that MI shouldn't be used to combine arbitrary classes. Or what do you mean by "union style MI"? > > In what way does the lack of MI affect the usefulness of the whole > > inheritance idea? *If* I think extensions of a base type should be > > done using inheritance, how do I solve the problem of combining > > independent extensions afterwards? > > You don't. But in general it is always wrong to combine >extentions which were not intended to be combined. Ada 9X will give >you a choice of several combining styles, and in general the language >will insure that mixtures which are permitted will work. However, >since generics mean that the difference between a combining extension >and normal single inheritance is a few words, you should honor the >wishes of the type designer and assume that two types which can't be >mixed shouldn't be mixed: > > [ ..example deleted.. ] > Yes and no. It is important to make a distinction between combining arbitrary extensions and extensions which should not be combined. IMHO, it is illegal to state that *if* I want to combine extensions, these possible extensions must be known to the base type. It's a quite natural situation that I want extensions to be mixable, but I cannot predict how many extensions there will be. Another example: In a tree, I have nodes. Every node is member of a node class. This class determines which attributes the node carries. Now, the classes are arranged into a hierarchy. I might want to build abstract syntax trees using this; with node classes for identifiers, statements (with appropriate subclasses for special statements) and the like. Now there are obvious occurences of MI in this example: An applied occurrence of an identifier in an expression is a subclass of identifier (i.e. carries the "name-of-identifier" attribute) as well as a subclass of the expression component, say factor (has e.g. a "value" attribute). I hope this clarifies my point. The writer of the base class for the nodes doesn't want to know in what way his class will be augmented; i.e. which node classes there will be and what attributes they have. But still, the type designer might want these to be combined. > If it weren't for the fact that generics are IMHO a much more >powerful tool than inheritance, I could argue that using generics to >implement mix-ins is like using a sledgehammer to swat flies. But >since Ada has all of the necessary support for generics for other >reasons, it seems silly to talk about adding MI because maybe someday >someone will think of an application where classical MI is >significantly better. (In my opinion, and that of a lot of other >software engineers, the ability to express "Watch it!" in the code is >a definite advantage. In Ada 9X using inheritance in a non-generic >fashion will be a strong warning message that this new type has more >than mix-in semantics.) > Sorry, but I still don't see how you handle polymorphism with generics. One last example on this: Suppose you have some container class, let's say a list. In this list, you want to store objects of different types. In the implementation of the list, you don't know what types, you don't even know how many. In fact, you *shouldn't* know this, because it has nothing to do with the list itself. Now, please, how do you do this with generics? Peter --- Peter Klein E-Mail: pk@rwthi3.informatik.rwth-aachen.de Lehrstuhl fuer Informatik III Tel.: +49/241/80-21320 Ahornstrasse 55 Fax.: +49/241/80-21329 RWTH Aachen D-5100 Aachen Germany