Re: Unconstrained Arrays problem Rick Duley <[log in to unmask]> Fri, 5 Feb 1999 12:17:29 +0800 text/plain (157 lines) ```        I received suggestions from Ben Brosgol, Steven Deller, David Hoos Sr, Sam Mize and Richard Riehle. Thanks folks for your rapid and helpful responses to my query. 1. On the matter of declaration of Unconstrained Arrays as 'limited private' there are two schools of thought:         Ben Brosgol reported: You can declare a private type with an "unknown discriminant part". The following example compiles and runs (I tried it under Aonix ObjectAda 7.1.2): --- package P is     type T(<>) is private;     function F(N : Integer) return T; private     type T is array(Positive range <>) of Integer; end P; package body P is     function F(N : Integer) return T is     begin         return T'(1..N => 0);     end F; end P; with P; use P; procedure Test_Unconstrained is     X : T := F(10); begin     null; end Test_Unconstrained;         and yet Steven Deller's response was: For item 1, my compiler tells me that for the following: package Trial3 is     type Case_Type is (Open, Shut);     type Uncon is private;     procedure Dumb (X : in out Uncon); private     type Uncon is array (Positive range <>) of Case_Type; end Trial3; " >>> Line 6: type Uncon is array (Positive range <>) of Case_Type" "*** array (Positive range <>) of Case_Type must be constrained [RM_95 7.3(12)]" -- oops! missed that! :( When I read 7.3(12) it states that "..., then the full_type_declaration shall define a definite subtype" (and a definite subtype requires array bounds).  That makes sense to me, since if code that used this package declared an object of type Uncon, there would be no way to determine the array bounds for that object. It is possible to use access types for Uncon, such that only the package body does any actual allocations of array entities, which may satisfy the original need you had: package Trial2 is     type Case_Type is (Open, Shut);     type Uncon is private; private     type Uncon_array is array (Positive range <>) of Case_Type;     type Uncon is access Uncon_array ; end Trial2; It is also possible to defer the definition of the Uncon_array into the body of the package: package Trial2 is     type Case_Type is (Open, Shut);     type Uncon is private;     procedure Dumb (X : in out Uncon); private     type Uncon_Array;     type Uncon is access Uncon_Array; end Trial2; package body Trial2 is     type Uncon_Array is array (Positive range <>) of Case_Type;     procedure Dumb (X : in out Uncon) is     begin         if X = null then             X := new Uncon_Array'(1 => Open, 2 => Shut);         end if;     end Dumb; end Trial2; 2. Declaration of a constant: There were two main variations on solutions.         Always_Guilty : constant Court_Type := (2 .. 1 => Shut);         as David Hoos commented "You have to specify a value for the array elements that aren't going to be there!"         Alternatively, as Sam Mize suggested: "...you can just declare it as a variable. After all, it's effectively constant -- you can't change any of the (non-existent) values!         Never_Guilty: Court_Type (2..1);         Richard Riehle made the point: "..., good object-oriented programming style would suggest that we abandon the use of deferred constants in our package designs. The usual form is something such as,       package P is           type T is private;           Empty_T : constant T;           -- more public stuff       private           full definitions of private stuff       end P;         "The more object-oriented way to approach this is to export a function for Empty_T in place of the deferred constant.              function Empty_T return T;         "This allows a variety of implementations on Empty_T, eliminates problems of dependencies when we change the values of the constants later, and improves maintainability. It also eliminates the need for the designer to fool around with syntax better left to the package implementor."         It seems there _are_ ways around the matter. Once again, thanks to all! -----------------------------------------------------------------------                                     ______ Rick Duley / \ Edith Cowan University (____/\ ) Perth, Western Australia |___ U?(____                                    _\L. | \ ___ ECU: +61 (08) 9370 6619 / /"""\ /.-' | |\ | mob: 0416 365 619 ( / _/u | \___|_)_|                                  \| \\ / / \_(___ __)                                   | \\ / / | | |                                   | ) _/ / ) | |                                   _\__/.-' /___( | | I think, _/ __________/ \ | | Therefore I am... // / ( ) | |                              ( \__|___\ \______ /__|____| I Think! \ (___\ |______)_/                                \ |\ \ \ /                                 \ | \__ ) )___/                                  \ \ )/ /__(                                   ___ | /_//___| \_________                                _/ ( / OUuuu \                               `----'(____________) ```