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.9 required=5.0 tests=BAYES_00,FREEMAIL_FROM autolearn=ham autolearn_force=no version=3.4.4 X-Google-Language: ENGLISH,ASCII-7-bit X-Google-Thread: 103376,436e4ce138981b82 X-Google-Attributes: gid103376,public X-Google-ArrivalTime: 2004-03-10 18:43:10 PST Path: archiver1.google.com!news2.google.com!news.maxwell.syr.edu!news.moat.net!border1.nntp.sjc.giganews.com!nntp.giganews.com!local1.nntp.sjc.giganews.com!nntp.comcast.com!news.comcast.com.POSTED!not-for-mail NNTP-Posting-Date: Wed, 10 Mar 2004 20:43:08 -0600 Date: Wed, 10 Mar 2004 21:43:08 -0500 From: "Robert I. Eachus" User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.0; en-US; rv:1.4) Gecko/20030624 Netscape/7.1 (ax) X-Accept-Language: en-us, en MIME-Version: 1.0 Newsgroups: comp.lang.ada Subject: Re: abstract sub programs overriding References: <1078776213.376775@master.nyc.kbcfp.com> <1078839257.157439@master.nyc.kbcfp.com> <5cmr40t76va200betf07b7bd6er05ltto9@4ax.com> <1078845298.702789@master.nyc.kbcfp.com> <0ipr40thtf86b520a0qdi003aj87gtuhd4@4ax.com> <1078849973.701176@master.nyc.kbcfp.com> <1078924150.268074@master.nyc.kbcfp.com> <1078934469.744922@master.nyc.kbcfp.com> <1078949096.760629@master.nyc.kbcfp.com> In-Reply-To: <1078949096.760629@master.nyc.kbcfp.com> Content-Type: text/plain; charset=us-ascii; format=flowed Content-Transfer-Encoding: 7bit Message-ID: NNTP-Posting-Host: 24.147.77.160 X-Trace: sv3-4hte5g0xYvIiVJlS3OMDZIZgjgLtuKvQDLwzZkNLXONvZw8o3KWIWB/n5GL2mi5qsuQEy0HU6czB/3m!jWwr1GqC52fSihGsdg/d9c/CI/GSJnnCD/CbMwBFtMjOoZwnF9TCQM3o1GEZKw== X-Complaints-To: abuse@comcast.net X-DMCA-Complaints-To: dmca@comcast.net X-Abuse-and-DMCA-Info: Please be sure to forward a copy of ALL headers X-Abuse-and-DMCA-Info: Otherwise we will be unable to process your complaint properly X-Postfilter: 1.1 Xref: archiver1.google.com comp.lang.ada:6223 Date: 2004-03-10T21:43:08-05:00 List-Id: Hyman Rosen wrote: > So he's not right, because it's not impossible, just very unusual. No, he is right. As a langauge lawyer I know how to "get around the rules." But counting something that you can do in a child package of Ada.Controlled or Ada.Limited_Controlled as a property of the language is silly. There are other ways to work around the rule, but they are similarly unlikely. So things that can be done with a user defined type derived from some other user defined type are interesting, but in the end at least one Intialize procedure will be called for all user defined controlled objects. > Anyway, let's see if I understand. You are saying that in Ada, it > is unusual to call Parent.Initialize(Parent_Type(Child_Object)) from > Child's Initialize. That seems odd to me; how does the child know that > the parent can do without this call? If it can be so blithely ignored, > what good is having it in the first place? No, as I said, there are two common idioms, the first is to call the parent Initialize AFTER doing any initialization work needed on the fields that occur only in the child. (The second is discussed below.) > You also say that "It is much more common, however, for such a call to > be done for only the parent part of the object, for example when creating > a child object using an aggregate." Isn't it the case that when you do > that, Child's Initialize won't be called at all? Yes, the parent object will be Initialized, and for a Controlled (not Limited_Controlled) aggregate assignment, the object created in this way will be Adjusted as a whole. But I think you missed my main point, that the Initialize procedure for the child type may use an extension_aggregate to create the object, then make any necessary adjustments, either explicitly or implicitly through the Adjust call made for regular Controlled types. Obviously you don't want the child's Initialize procedure to be called on extension_aggregates, because an extension_aggregate may necessary inside the Initialize procedure of the child type. Sort of a meta comment here, and it goes back to what I said above. All objects of types descended from Controlled or Limited_Controlled have fields that are not visible to an ordinary user. This means that for most users what they can do in a child package of Ada.Controlled is of limited interest. This is really what makes the only interesting cases: procedure Initalize(Object: in out Child) is begin Do_Something(Object); Initialize(Parent(Object)); end Initialize; or: procedure Initialize(Object: in out Child) is begin Object := (Parent_Type with ...); Do_Something_Else(Object); end Initialize; Now notice that it is trivially obvious that in Do_Something or Do_Something_Else, Object is not fully initialized. But we are inside the Initialize procedure, so of course it hasn't completed yet. As a programmer it is not hard to choose whichever idiom is appropriate for the type you are defining. But it is also the case that for any controlled Object users cannot bypass the first stage of initialization, where Object is created and all components are initialized to their default values. (Or in the extension aggregate case, given valid non-default values.) So yes, there are areas where user written code can access an object that has not yet been completely initialized. But in practice, as a user you will find that once you get rid of any bugs (and exceptions) inside Intialize, Adjust, and Finalize, that code written by others, including the authors of types derived from your types, cannot mess up the invariants of your type. > You also say that as a matter of policy, Initialize should not make > a dispatching calls because it is likely to be incorrect. That's what > C++ avoids by preventing dispatching from going to parts of the final > object which are not yet constructed. No, I did not say that. I said that attempts to down convert an object to a child type will fail. Technically, it is not possible to do a VALUE conversion from a parent type to a (tagged) child type. You will find that in some cases a view conversion is legal, but an attempt to assign to that view will often raise Constraint_Error (or Program_Error). I am not going to try and describe here when conversions are illegal, when they will raise Program_Error, and when they will raise Constraint_Error. All that is spelled out in RM 4.6, and it is hard to say it in fewer words. (RM 4.6 is cryptic enough! You might want to use the AARM instead: http://www.adaic.org/standards/95aarm/html/AA-4-6.html) So what I was saying was that it is possible to put an view conversion to a child type inside an Initialize procedure, but if you try to write the code, you will find yourself dodging lots of land mines. For example, the body of the package which defines the parent type is going to have to with the package that defines the child type. But if you are not very careful, there will be no valid elaboration order for the corresponding package bodies. There are lots of land mines that have nothing to do with the issues you are trying to raise here that can come up if you try what you indicated. It is like discussing the speed at which you can drive southbound down the northbound side of a divided highway. You may be interested in whether or not the banking of the curves works correctly. However, there are going to be lots of impediments to doing the actual experiment that have nothing to do with curves, banking, or automobile suspensions. (They would have something to do with license suspensions though. ;-) -- Robert I. Eachus "The only thing necessary for the triumph of evil is for good men to do nothing." --Edmund Burke