comp.lang.ada
 help / color / mirror / Atom feed
From: ncohen@watson.ibm.com (Norman H. Cohen)
Subject: Re: OO Idiom: Interfaces for derived classes
Date: 1996/03/22
Date: 1996-03-22T00:00:00+00:00	[thread overview]
Message-ID: <4ium18$113p@watnews1.watson.ibm.com> (raw)
In-Reply-To: mmannvijxa4ta.fsf@ibm.net

In article <mmannvijxa4ta.fsf@ibm.net>, mmann@ibm.net (Gerd Moellmann) writes: 

|> Yes, the proposal requires voluntary compliance (which can be easily
|> checked if necessary) and it requires programmers to take an explicit
|> action---with'ing base_package.derived---to gain access to base class
|> internals.
...
|> If we talk about "trusting" (I am not concerned about programmers
|> cluttering up something intentionally; I am primarily aiming at
|> getting a less coupled implementation with my proposal): 
|>
|> Don't class libraries, frameworks/patterns often require users to
|> derive classes from library classes?  Can it always be foreseen from
|> which classes it might be desirable to derive new classes?  The
|> "trusting scheme" would have to trust quite a lot of people, IMO.
...
|>                       I think of an application programmer using, say,
|> one class library for the user interface, another for database access,
|> and yet another one for communications.  If I had the choice to
|> either protect her against inadvertantly relying on non-public
|> features of one of maybe several hundred classes or trust her, I would
|> prefer the first alternative.

Okay, I see the value of your scheme as a way of making explicit those
features of the parent package that are part of the documented interface
for descendents.  Adherence to this interface can be easily enforced by a
combination of fine-grained compiler checks and coarse-grained checks
about program structure in the large by another tool.

I wrote: 

|> > The situation gets more complicated when we turn our attention from a
|> > snapshot, or release, of a program to a program as an living entity that
|> > evolves over time, or to the distribution as a reusable component of a
|> > package providing some OO class.  Then it becomes important for the
|> > writer of the parent package to provide documentation distinguishing
|> > those aspects of the parent package that represent supported parts of its
|> > interface from those parts of the parent package that represent
|> > implementation choices that may change in future releases of the parent
|> > package.  At one extreme, the writer of the parent might guarantee the
|> > proper functioning of the package only as long as no children are written
|> > for it.  At the opposite extreme, the writer of the parent may commit to
|> > preserving all the declarations in the private part of the package in all
|> > future releases.  But the child should ask not (just) what the parent can
|> > do for it; the child should ask too what it can do for (or to) its
|> > parent:  If the writer of the parent does not rule out child packages
|> > entirely, he must also document those invariants that all children of the
|> > package must preserve if the package is to continue to function
|> > correctly.

You responded: 

|> Agreed. This is true no matter how you implement derived classes.

If child packages are forbidden by convention and all of the exported
operations are understood to be a part of the documented interface (i.e.,
their inclusion in the interface represents a commitment that they will
continue to be supported in future versions of the package) and the
operations preserve the necessary invariants, then in fact it is not a
concern:  Any subclass or ordinary client using the class is doing so in
a supported manner.

|> > Back to the idiom you propose:  The usual reason for a derived class
|> > referring directly to members of a base class is efficiency.
|>
|> You can gain efficiency in my scheme by inlining subprograms.

True.

|> > If you are
|> > going to force all manipulations of the base-class implementation to be
|> > through subprograms exported by Base_Package.Derived anyway, you lose the
|> > motivation for giving implementations of derived classes special
|> > privileges. Why distinguish then between operations that are acceptable
|> > only for derived classes to perform and those that are acceptable for all
|> > clients to perform?  If you have truly hidden the implementation of the
|> > base class from derived classes, then it would seem that any operation
|> > deemed safe for the implementation of the derived class to perform will
|> > also be safe enough for the world at large to perform.  If you have a
|> > specific example that suggests otherwise, it would be interesting to
|> > see it.
|>
|> To cite [Rumbaugh, Object Oriented Modeling & Design, 1991 (p.322)],
|> (hope I got the name right:-), and this the intention behind my proposal: 
|>
|> "....
[first paragraph of quote deleted]
|>
|> Often it is useful to write some "private" operations that are for
|> internal use only by other methods of the same class. It is desirable
|> to restrict the visibility of these operations so that other classes
|> cannot use them.  It is often necessary to allow subclasses to access
|> these internal operations, so a simple distinction between public and
|> private is not possible..."

It is the second sentence above that I question.  If your goal is to make
the world safe for subclass writers, then these "internal-use" operations
had better respect the invariants of the implementation.  If they do so,
what is the harm in making them available to the world at large?  After
all, if they are potentially useful to implementers of subclasses, they
are potentially useful to ordinary clients as well.

That avoids the complications of writing a special child package for use
by subclasses only, ensuring that these special child packages are the
only child packages (ensuring that there are NO child packages is simpler
matter), and ensuring that these special child packages are imported only
to implement subclasses.

Again, I would be interested in seeing a compelling specific
counterexample.

|> Thank you for your answer, Norman.  Although it didn't convince me to
|> drop my proposal it was interesting to hear your opinions.  May I add
|> a congratulation for your really fine book "Ada as a 2nd language"?

Thank you!

--
Norman H. Cohen    ncohen@watson.ibm.com




  reply	other threads:[~1996-03-22  0:00 UTC|newest]

Thread overview: 7+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
1996-03-21  0:00 OO Idiom: Interfaces for derived classes Gerd Moellmann
1996-03-21  0:00 ` Norman H. Cohen
1996-03-22  0:00   ` Gerd Moellmann
1996-03-22  0:00     ` Norman H. Cohen [this message]
  -- strict thread matches above, loose matches on Subject: below --
1996-03-22  0:00 Jean-Pierre Rosen
1996-03-22  0:00 ` Norman H. Cohen
1996-03-22  0:00 ` Gerd Moellmann
replies disabled

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox