From: Ludovic Brenta on 15 Mar 2010 09:04 cjpsimon(a)gmail.com wrote on comp.lang.ada: > On 15 mar, 10:14, Ludovic Brenta <ludo...(a)ludovic-brenta.org> wrote: >> (1) pass Dirty as "access" instead of "in out": works but, as you >> nicely put it, "One of the nice things about Ada over other languages >> is that you generally shouldn't >> have to worry about whether a parameter is copy-by-value or copy-by- >> reference." > >> (2) pass Dirty encapsulated in a limited record: also works but this >> is even worse (IMHO) than "access" because it obscures the purpose of >> the limited record type. I'd have to have 10 lines of comments just to >> explain why there is a limited record type containing a single Boolean >> component. > >> (3) make Dirty part of the object type T: the flag is necessary in >> only one of the places where T is used; also T is serialized in >> several places, so changing it is not a good idea. > >> (4) handle the exception in the caller: there is no longer a central >> place for handling the Dirty flag therefore future maintenance is >> harder. As a side effect, the procedure Refresh loses most of its >> purpose, so might as well disappear. > >> I came up with (5): place both Dirty and the Object to be visited in a >> record type and pass an access value to that record. This is a >> variation of (1); it is still ugly (IMHO) but the record type and the >> access-to-record type already existed so the change to the code base >> was minimal. Since, however, the existing record type contains many >> other things besides the Object and Dirty flag, the procedure Refresh >> receives much more information than it really needs, which might break >> encapsulation. [...] > May be a (6) option is to create a tagged type ? I see this as a variant of (2) and has the same drawbacks. In this case I would have to explain why I use a tagged type that has no primitive operations (the procedure Refresh does not have to be primitive for this type) and no type extensions . -- Ludovic Brenta.
From: J-P. Rosen on 15 Mar 2010 10:16 Ludovic Brenta a �crit : >> May be a (6) option is to create a tagged type ? > > I see this as a variant of (2) and has the same drawbacks. In this > case I would have to explain why I use a tagged type that has no > primitive operations (the procedure Refresh does not have to be > primitive for this type) and no type extensions . > Proposal (7): Make Dirty a (limited) private type -say Status- with functions Is_Dirty and Is_Clean. You are then free to implement it as a by-reference type. If it's a mess, hide it... -- --------------------------------------------------------- J-P. Rosen (rosen(a)adalog.fr) Visit Adalog's web site at http://www.adalog.fr
From: Robert A Duff on 15 Mar 2010 12:44 Ludovic Brenta <ludovic(a)ludovic-brenta.org> writes: > No, Dirty is not a property of the object; the type T is used in > several places, only some of which (a one-line cache, essentially) has > a Dirty property. OK, then Dirty is a property of the cache. So how about: type Cache is limited record X : T; Dirty : Boolean := True; end record; type Cache_Ref is access all Cache; and pass a parameter of type Cache_Ref? (Or perhaps X could be an access type, and point to the T object.) You need to pass some sort of pointer, explicitly or implicitly, because when you raise an exception, the copy-back is skipped. You said that relying on limitedness to force pass-by-referrence is confusing -- I agree. So pass an explicit pointer. I recommend a named access type, because anonymous access parameters have dynamic accessibility, which is a tripping hazard, and is less efficient. - Bob
From: Ludovic Brenta on 15 Mar 2010 13:33 Robert A Duff wrote on comp.lang.ada: > Ludovic Brenta <ludo...(a)ludovic-brenta.org> writes: > > No, Dirty is not a property of the object; the type T is used in > > several places, only some of which (a one-line cache, essentially) has > > a Dirty property. > > OK, then Dirty is a property of the cache. So how about: > > type Cache is limited > record > X : T; > Dirty : Boolean := True; > end record; > type Cache_Ref is access all Cache; > > and pass a parameter of type Cache_Ref? (Or perhaps > X could be an access type, and point to the T object.) > > You need to pass some sort of pointer, explicitly or implicitly, > because when you raise an exception, the copy-back is skipped. > You said that relying on limitedness to force pass-by-referrence > is confusing -- I agree. So pass an explicit pointer. > > I recommend a named access type, because anonymous access parameters > have dynamic accessibility, which is a tripping hazard, and is > less efficient. Yes, that's the solution I have, currently, i.e. (5); except that the Cache type already existed before, has other unrelated components and is not limited. -- Ludovic Brenta.
From: Robert A Duff on 15 Mar 2010 14:36
Ludovic Brenta <ludovic(a)ludovic-brenta.org> writes: > Robert A Duff wrote on comp.lang.ada: >> Ludovic Brenta <ludo...(a)ludovic-brenta.org> writes: >> > No, Dirty is not a property of the object; the type T is used in >> > several places, only some of which (a one-line cache, essentially) has >> > a Dirty property. >> >> OK, then Dirty is a property of the cache. �So how about: >> >> � � type Cache is limited >> � � � � record >> � � � � � � X : T; >> � � � � � � Dirty : Boolean := True; >> � � � � end record; >> � � type Cache_Ref is access all Cache; >> >> and pass a parameter of type Cache_Ref? �(Or perhaps >> X could be an access type, and point to the T object.) >> >> You need to pass some sort of pointer, explicitly or implicitly, >> because when you raise an exception, the copy-back is skipped. >> You said that relying on limitedness to force pass-by-referrence >> is confusing -- I agree. �So pass an explicit pointer. >> >> I recommend a named access type, because anonymous access parameters >> have dynamic accessibility, which is a tripping hazard, and is >> less efficient. > > Yes, that's the solution I have, currently, i.e. (5); except that the > Cache type already existed before, has other unrelated components and > is not limited. Right, but you said you didn't like it, because of the "other unrelated components". So the type I'm suggesting above is a different one than the existing one -- I'm suggesting this new type would NOT have the unrelated components. I haven't seen your code, of course, so I could be talking complete nonsense. ;-) - Bob |