From mboxrd@z Thu Jan 1 00:00:00 1970 X-Spam-Checker-Version: SpamAssassin 3.4.4 (2020-01-24) on polar.synack.me X-Spam-Level: X-Spam-Status: No, score=-1.3 required=5.0 tests=BAYES_00,INVALID_MSGID autolearn=no autolearn_force=no version=3.4.4 X-Google-Language: ENGLISH,ASCII-7-bit X-Google-Thread: 103376,a3471634bf10bf8d X-Google-Attributes: gid103376,public From: "Samuel T. Harris" Subject: Re: private type discriminants ignored? Date: 1998/04/28 Message-ID: <35460201.ED1315C4@hso.link.com>#1/1 X-Deja-AN: 348455987 Content-Transfer-Encoding: 7bit References: Mime-Version: 1.0 Content-Type: text/plain; charset=us-ascii Organization: Raytheon Training Inc. Newsgroups: comp.lang.ada Date: 1998-04-28T00:00:00+00:00 List-Id: Robert A Duff wrote: > > In article , > Jay Sachs wrote: > > type Stack(Size : Integer := 100) is private; > > >... What is the reason that the default initialization > >seems to be ignored in the discriminant for the private type? > > The default isn't being ignored; Size is being correctly initialized to > 100. However, the mere presence of a default means that the > discriminant can change. That's confusing, and is a language design > flaw, IMHO. There should have been a separate keyword or some other > separate syntax to mean "the discrim might change". But as it is in > Ada, an unconstrained variable of type Stack can later have a discrim of > Integer'Last, even though it defaults initially to 100. And many > compilers take the (quite reasonable) attitude that implicit heap > allocation is evil, so they allocate the maximum possible size for these > things. And in this case, that's enormous, and will typically raise > Storage_Error; hence the warning. Not entirely accurate. The mere presense of the default value does not mean the discriminant can change. It depends on how objects are declared. The discriminant can only change if the subtype indication used to declare an object does not specify its value. Such as ... my_stack : stack; The subtype indication "stack" provides no value for the discriminant so the default is used. Because the subtype indication does not "lock" down the value, the discriminant can indeed change when the whole object is assigned. The discriminant cannot change by itself as in ... my_stack.size := 1000; -- Compilation error. Because the discriminant can change, I expect a compiler to allocate an amount of memory needed for the worst size case. However, if I define ... your_stack : stack(100); ... then the discriminant cannot change, even when assigne the entire object, and I do not expect the compiler to allocate to worst case amount of memory. I expect it to allocate only enough memory for a stack of 100 elements. In any event, I treat Robert Duff's advice below as gospel. All types should be constrainted according to their requirements. This lets the compiler catch many potential problems. > > If you want stacks that can range from 0 to 1000, with a default of 100, > try: > > type Stack_Length is range 0..1000; > type Stack (Length: Stack_Length := 100) is ... > > But this will allocate 1000 elements, when perhaps only 100 are needed. > If you really want the size to change, but you want the amount allocated > to reflect the current size, you'll need to use access types. If you > just want a default of 100, but never want the size to change, don't use > defaults: > > type Stack(Length: Natural) is ... > subtype Default_Stack is Stack(Length => 100); > X, Y: Default_Stack; > Huge_Stack: Stack(Length => 100_000); > > - Bob > -- > Change robert to bob to get my real email address. Sorry. -- Samuel T. Harris, Principal Engineer Raytheon Training Incorporated "If you can make it, We can fake it!"