comp.lang.ada
 help / color / mirror / Atom feed
From: "David C. Hoos, Sr." <david.c.hoos.sr@ada95.com>
Subject: Re: premature use of private
Date: 1999/08/17
Date: 1999-08-17T00:00:00+00:00	[thread overview]
Message-ID: <lOau3.6055$x04.351489@typ11.nn.bcandid.com> (raw)
In-Reply-To: In2u3.3680$z6.293053@typhoon-sf.snfc21.pbi.net


<tmoran@bix.com> wrote in message
news:In2u3.3680$z6.293053@typhoon-sf.snfc21.pbi.net...
> I'm given an existing program that processes Apples with routines like
>   function Is_Ripe(X : Apple) return Boolean;
>   function Is_Red(X : Apple) return Boolean;
>   function Size(X : Apple) return Integer;
> and
>   type Pile is array(integer range <>) of Apple;
>   procedure Sort_By_Size(X : in out Pile);
>
> I now need to add Oranges and Grapefruit and ...
> So I tried
>
>   type Fruit is abstract tagged private;
>   function Is_Ripe(X : Fruit) return Boolean;
>   function Size(X : Fruit) return Integer;
>
>   type Apple is new Fruit with private;
>   function Is_Red(X : Apple) return Boolean;
>
>   type Orange is new Fruit with private;
>   function Florida(X : Orange) return Boolean;
>
> So far so good.  But I don't want a Pile of mixed Fruit, so,
> borrowing from Barnes' on Containers, I tried:
>
>   generic
>     type This_Fruit is abstract tagged private;
>     type Fruit_Ptr is access all This_Fruit;
>   package Sets is
>     type Pile is array(integer range <>) of Fruit_Ptr;
>     procedure Sort_By_Size(X : in out Pile);
>   end Sets;
>
>   type Apple_Ptr is access all Apple;
>   package Apples is new Sets(Apple, Apple_Ptr);
>
> But that won't work because Apple is private at this point.
>
>   How should this be done?

A generic instantiation can be declared (at least with GNAT)
only at a point where the body(ies) of the actual type(s)
with which it is instantiated are available;

Further, it seems to me that to provide for new extensions
without alteration of existing source files, the derived types
should be in their own packages.

Third, it seems that Size and Is_Ripe are intended to be class-wide
functions, and should therefore have formal parameters of Fruit'Class;
Alternatively, if they are not class-wide, they should be declared
abstract so as to require overriding in any type derived from Fruit.

Fourth, based on the English meaning of the identifiers, it doesn't
seem that Sort_By_Size would need to be generic, nor that other
operations on sets of fruit would need (nor could be) specialized
for (as yet) undefined derived types, but perhaps the real abstraction
is different.

Having said all that, here's a skeleton of how I would approach it,
not knowing any more about the abstraction.

package Fruit is

   type Fruit is abstract tagged private;

   function Is_Ripe (X : Fruit'Class) return Boolean;
   function Size (X : Fruit'Class) return Positive;

   generic
      type This_Fruit is new Fruit with private;
      type Fruit_Ptr is access all This_Fruit;
   package Sets is
      type Pile is array (Positive range <>) of Fruit_Ptr;
      procedure Sort_By_Size (X : in out Pile);
   end Sets;

private
   type Fruit is tagged record
      Ripe : Boolean;
      Size : Positive;
   end record;
end Fruit;

package Fruit.Apples is

   type Apple is new Fruit with private;
   function Is_Red (X : Apple) return Boolean;

   type Color is (Green, Red, Yellow);
private

   type Apple is new Fruit with record
      Col : Color;
   end record;
end Fruit.Apples;

package Fruit.Oranges is
   type Orange is new Fruit with private;
   function Florida (X : Orange) return Boolean;
   type Origin is (California, Florida);
private
   type Orange is new Fruit with record
     Orig : Origin;
   end record;
end Fruit.Oranges;

with Fruit.Apples;
with Fruit.Oranges;
procedure Do_Things_With_Fruit is
   type Apple_Ptr is access all Fruit.Apples.Apple;
   package Apples is new Fruit.Sets (Fruit.Apples.Apple, Apple_Ptr);
begin
   null;
end Do_Things_With_Fruit;






      parent reply	other threads:[~1999-08-17  0:00 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
1999-08-17  0:00 premature use of private tmoran
1999-08-17  0:00 ` Matthew Heaney
1999-08-17  0:00   ` tmoran
1999-08-17  0:00     ` David C. Hoos, Sr.
1999-08-18  0:00     ` Matthew Heaney
1999-08-18  0:00       ` tmoran
1999-08-18  0:00         ` Matthew Heaney
1999-08-17  0:00 ` David C. Hoos, Sr. [this message]
replies disabled

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