Path: utzoo!utgpu!jarvis.csri.toronto.edu!mailrus!wuarchive!gem.mps.ohio-state.edu!ginosko!uunet!mcsun!sunic!dkuug!daimi!jlk@daimi.dk
From: jlk@daimi.dk (Jorgen Lindskov Knudsen)
Newsgroups: comp.lang.c++
Subject: Re: conceptual problem with related classes derived in parallel
Keywords: help, thanks
Message-ID: <3372@daimi.dk>
Date: 3 Oct 89 08:40:26 GMT
References: <1071@godot.radonc.unc.edu>
Sender: news@daimi.dk
Reply-To: jlk@daimi.dk (Jorgen Lindskov Knudsen)
Organization: DAIMI: Computer Science Department, Aarhus University, Denmark
Lines: 120
In-reply-to: sherouse@godot.radonc.unc.edu (George W. Sherouse)

In article <1071@godot.radonc.unc.edu> George W. Sherouse writes:
>
>Consider a class used for maintaining dynamically-allocated lists of
>things.
>
... Various class definitions deleted ...
>Or, schematically:
>
>	list         -- points to ->        element
>         |                                     |
>       derive                               derive
>	 v                                     v
>      new_list  -- would like to access -> new_element
>
>The intent here is to reuse list maintenance code from the base
>list_of_element class in the derived list_of_new_element class which
>operates on the dervived data class new_element.  The scheme above
>does not work because for either class of list this->list[n] is always
>an instance of the base element class.  Without a cast,
>new_list_manipulator will not be able to access other_data.
>Similarly, add_element_to_list will not be able to divine the correct
>size for the elements.
>
>A number of solutions come to mind, but none particularly satisfying
>from a philosophical point of view.
>
... stuff deleted ...
>This same problem in a number of different guises has cropped up in
>different parts of a project we are working on.  Are we missing
>something obvious here?  Are we missing something subtle?  It appears
>that what we are really looking for is support for virtual data types.
>Any help out there?

And in article  David Detlefs writes:

>Congratulations!  You have reached a state of object-oriented
>enlightenment in which you realize that inheritance is not the
>solution to all software organization problems.  This is a good thing.
>Only zealots would claim otherwise.
>
>What you really want here is a "parameterized type."  In some future
>version of C++ you will be able to write something like
>
>template  class list {
>  protected:
>    T* elems;
>  public:
>    void add_elem(T elem);
>}
>
>Which you could then use by simply writing
>
>list or list as a type in your code.  In your example, there was
>no obvious reason why "element" and "new_element" were related by
>inheritance, other than that you thought they should be in order to
>make the list work.  In this scheme, you can leave them as unrelated
>types, unless there really is a good reason to derive new_element from
>element.
>
>As I said, Parameterized types are a future feature, but for the time
>being, you can get the same effect by writing list as a
>preprocessor macro (or 2 macros, one for the declaration and one for
>the definition).  See Stroustrup p. 210.
>
>Hope this helps.

There is another side of this coin, namely that the generality of most
objetc-oriented languages of today isn't sufficient.  That is, the problem
pointed out by George W. Sherouse is indeed an object-oriented problem, but
without solutions in C++.  George W. Sherouse is also thinking in the right
direction, when he is seeking for virtual data types.

Solutions by means of parameterized types or macros can be usefull in many
respects, but if used to solve problems within the object-oriented framework,
they seem counterintuitive.  Just to name one significant problem, you might
consider the problem of parameterized types not being first-class citizens of
the language, implying than you are unable to create code that enables you to
manipulate the types on the level of the parameterized type, but is forced
allways to work on the level of the concrete type.

The BETA language (a tutorial is being held on that language on OOPSLA tpday)
supports the specification of virtual classes.  The language is documented
various places, e.g. in Wegner & Shriver (Eds.): Research Directions in
Object-Oriented Programming, MIT Press, 1987.  The solution to your problem
would in Beta be (except for minor syntactical issues):

element: class (# data: @data_type; 
		  data_accessor: virtual proc (# ... #):
	       #)

new_element: class (# other_data: @other_data_type #);

list_of_elements: class (# element_type: virtual class element;
			   list: ^element_type;
			   add_element_to_list: proc(e: element_type) (# ... #)
			#)

list_of_new_elements: list_of_elements class (#
			   element_type: extended class new_element;
			   new_element_manipulator: proc() (# ... #);
			#)

Now, list_of_new_elements will be hold new_element objects, and
new_element_manipulator will be able to securely access other_data (strongly
typed).

For further information on virtual classes, see the paper by Ole Lehrmann
Madsen and Birger Moller-Pedersen: Virtual Classes: a Powerfull Mechanism in
Object-Oriented Programming, OOPSLA'89 (will be presented on Friday).
-- 
---> Jorgen Lindskov Knudsen / jlknudsen@daimi.dk
---> Computer Science Department, Aarhus University
---> Ny Munkegade 116, DK-8000 Aarhus C, DENMARK
---> Phone: +45 86 12 71 88 / telefax: +45 86 13 57 25 / telex: 64767 aausci dk


---> Jorgen Lindskov Knudsen / jlknudsen@daimi.dk
---> Computer Science Department, Aarhus University
---> Ny Munkegade 116, DK-8000 Aarhus C, DENMARK
---> Phone: +45 86 12 71 88 / telefax: +45 86 13 57 25 / telex: 64767 aausci dk