comp.lang.ada
 help / color / mirror / Atom feed
From: Stephen Leake <stephen_leake@stephe-leake.org>
Subject: Re: Access types as parameters
Date: Wed, 22 Jul 2009 22:11:29 -0400
Date: 2009-07-22T22:11:29-04:00	[thread overview]
Message-ID: <u63dkb12m.fsf@stephe-leake.org> (raw)
In-Reply-To: 8880c3d0-a07f-4d4e-ac87-372014598576@d15g2000prc.googlegroups.com

Adam Beneschan <adam@irvine.com> writes:

> For a procedure, there's less reason to do so.  I don't know anything
> about GTK, so I don't know why this wouldn't have worked, if all
> Initialize is doing is to set up some fields in Button:
>
> procedure Initialize
>               (Button : in out Gtk_Button_Record'Class;
>                Label  : UTF8_String);
>
> If, on the other hand, Initialize needs Button as an access so that it
> can store it in a data structure, then it probably would have been
> best to make it a named access type, to ensure that dangling
> references aren't stored in that data structure.

Most GTK subprograms do need access values; the same is true of any
system that deals with derived types at multiple levels. The only
library-level object that can hold any type in the hierarchy is a
class-wide pointer. Lists of objects must hold pointers, etc.

So one reason to use 'access' instead of 'in out' is simply to avoid
the user having to type '.all' everywhere.

A reason to use 'access Record_Type' instead of 'in Access_Type' is to
avoid explicit type conversions. Given:

package Widget is
    type Gtk_Widget_Record is ...;
    type Gtk_Widget is access all Gtk_Widget_Record'class;

    procedure Show (Widget : in Gtk_Widget);
end Widget;

package Window is
    type Gtk_Window_Record is new Gtk_Widget_Record with ...;
    type Gtk_Window is access all Gtk_Window_Record'class;
end Window;

    Window : Gtk_Window := ...;

then this does not work:

   Widget.Show (Window);

but this does:

   Widget.Show (Gtk_Widget (Window));

This is just annoying!

However, if Show is declared:

procedure Show (Widget : access constant Gtk_Widget_Record'class);

Then Show matches any access type in the class hierarchy; 

    Widget.Show (Window); 

works. 

In addition, leaving out the 'class makes Show a primitive operation,
which has many advantages.

I've been struggling with this issue in OpenToken, and settled on
using 'access Record_Type' as the best compromise. Now I just need to add
'constant' in all the right places; that wasn't allowed in Ada 95,
when OpenToken was first written.
    
In some cases, I have both class-wide and primitive operations:

   type Instance is abstract tagged private;
   subtype Class is Instance'Class;
   type Handle is access all Class;

   function Name (Token : in Instance) return String is abstract;

   --  Dispatching calls to Name
   function Name_Dispatch (Token : in Class) return String;
   function Name_Dispatch (Token : access constant Instance'Class) return String;

That gives the best of all cases, at the expense of writting more
code.

> And if you're going to store the access parameter in a global
> structure, you'll get a runtime error if you try to store a dangling
> reference, so it's best to use a global access type so that
> accessibility level errors are caught at compile time.  

This is a problem; people keep stumbling across it. Still, you get
used to it after a while, and stop trying to pass 'access of a local
variable.

-- 
-- Stephe



  reply	other threads:[~2009-07-23  2:11 UTC|newest]

Thread overview: 31+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2009-07-17  8:39 Access types as parameters Rick
2009-07-17 15:03 ` Adam Beneschan
2009-07-17 16:28   ` Hibou57 (Yannick Duchêne)
2009-07-17 23:25     ` rickduley
2009-07-18  1:03       ` Randy Brukardt
2009-07-19 22:57         ` rickduley
2009-07-20  0:10           ` John B. Matthews
2009-07-20  8:13           ` Dmitry A. Kazakov
2009-07-21  0:34           ` Randy Brukardt
2009-07-21 14:34           ` Adam Beneschan
2009-07-23  2:11             ` Stephen Leake [this message]
2009-08-11 23:41               ` Randy Brukardt
2009-08-12  2:22                 ` Stephen Leake
2009-08-13  1:06                   ` Randy Brukardt
2009-08-13  8:34                     ` Niklas Holsti
2009-08-13  9:15                       ` Dmitry A. Kazakov
2009-08-13 20:13                         ` Niklas Holsti
2009-08-13 21:07                           ` Dmitry A. Kazakov
2009-08-14  9:27                             ` Niklas Holsti
2009-08-14 10:36                               ` Dmitry A. Kazakov
2009-08-14 16:03                                 ` Niklas Holsti
2009-08-15  9:47                                   ` Dmitry A. Kazakov
2009-08-15 19:19                                     ` Niklas Holsti
2009-08-16  8:32                                       ` Dmitry A. Kazakov
2009-08-16  9:52                                         ` Niklas Holsti
2009-08-16 12:38                                           ` Dmitry A. Kazakov
2009-08-16 13:21                                             ` Niklas Holsti
2009-08-16 17:58                                               ` Dmitry A. Kazakov
2009-08-14  4:07                       ` Randy Brukardt
2009-08-14 10:22                         ` Niklas Holsti
2009-08-18 12:22                     ` Stephen Leake
replies disabled

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