comp.lang.ada
 help / color / mirror / Atom feed
From: "per" <commander@death-star.com>
Subject: Re: OO problem: Performing actions on messages (very long, sorry)
Date: 5 Jan 2005 04:01:18 -0800
Date: 2005-01-05T04:01:18-08:00	[thread overview]
Message-ID: <1104926478.797780.7830@c13g2000cwb.googlegroups.com> (raw)
In-Reply-To: cbqe9mwbnb6g.xlhb5hpreghg.dlg@40tude.net

Dmitry, guess what, your solution helped me make my *first* solution
(with access to Put-procedures) work!

The key point was the contract on generic Message_Type and the type
conversion in Execute:

generic
type Message_Type is new Message with private;

...

procedure Execute(Self : in out Instance;
M    : in Message.Class_Reference) is
begin
This.OverrideMethodRef(Message_Type(M.all), Self.Argument);
end;

It may not be the most elegant Ada-ish solution, but my initial idea
works and that's encouraging at least.

Dmitry:

...

>>>     Put (Message_Type'Class (Message), This.Argument);
>
>Remember the rule? The above of course should be
>
>Put (Message_Type (Message), This.Argument);
>
>sorry again!
>
>The reason is that Put is not dispatching, because we pass it
explicitly as
>a generic parameter. It is logical that then it cannot dispatch on
>Message_Type'Class. The compiler should complain. Ada is a safe
language!

It did :)

...

>> I see! So you're saying that I need one instantiation for each
>> *Put-procedure* and message (instead of one for each *type* and
>> message)? Hm, that's a lot of instances in my system...

>Right, generics are said to be statically polymorphic, to underline
that
>there is a better, true polymorphism. (:-))

OK, I agree true polymorphism is preferable.

Do you dare to say that ALL generics *could* be implemented with true
polymorphism?

If so, do you dare to say that ALL generics *should* be implemented
with true polymorphism? (Just curious.)

>I would try to get rid of generics. The main problem why generics
appear in
>your case is that you have parallel type hierarchies. No language, I
know
>of, can gracefully handle that. Remove parallelism and things will
become
>much simpler. For example,
>
>1. If the number of different argument types is limited, you could
make all
>possible variants of Put primitive operations of Message:
>
>type Message is abstract tagged ...
>procedure Put (M : in out Message; Value : Ihteger);
>procedure Put (M : in out Message; Value : Float);

But... What if the descendant to Message has many fields of the same
type (as definitely is the case for me):

type Message.M1 is new Message with
record
A : Integer;
B : Integer;
end;

What field would be assigned by

procedure Put (M : in out Message.M1; Value : Integer);

?

...

>2. Another axis is that action have to contain message of potentially
>unknown type. You already handled that by declaring a common ancestor
for
>all messages. So you could aggregate Message'Class into Action instead
of
>doing so for a specific Message. The latter requires generics, the
former
>does not. Though you cannot do it directly: (*)
>
>type Override (Argument : access Message'Class) is new Action with
record
>  Argument : Message'Class; -- This is not Ada!!
>end record;
>
>But you can use mix-in:
>
>type Override (Argument : access Message'Class) is new Action ...;
>
>Here each instance of Override has a "pointer" (access discriminant)
to its
>message. This approach might become difficult when the scope of action
is
>not nested in one of the message. Also it would require Action to be a
>limited type. So, alternatively you can make reference counting for
>messages and have handles (smart pointers) to them in actions. There
are
>ready-to use implementations of smart pointers in Ada. With this
approach
>you can pass a handle to message instead of the message object. For
example
>Override would just assign one handle to another without any copying.
In
>some cases it might become much more efficient than parameter
marshaling,
>which is what I suppose you are trying to do. The price to pay is that
you
>will need to handle aliasing, concurrent changes of a message etc.

OK, some of this is a bit beyond my Ada knowledge I'm afraid (remember
I'm still an Ada newbie ;), but I kind of get your point. Lots of new
stuff for me so next questions may be stupid:

Would this approach cope with that the actions are not connected to a
certain message *instance* until the point the action should execute?
The action at most only "knows" what *type* (or should I say class) of
message it should execute upon, and the message instance existsonly
close (in time) to the moment the action executes and not under the
actions entire life-time.

When you say "For example Override would just assign one handle to
another without any copying" it seems that you mean a handle to an
entire message? If so, that's not what an override action is supposed
to. Only a single field *inside* the message should be overridden. Or
have I misunderstood you completely?

I would like to avoid lots of copying since the system is a real-time
simulator so  using handles is tempting. In practice I think most
parameters will be "small" though (Integer, Float, bitfields etc) so
it's not a big deal.

>----
>* If action is not a descendant of message. This is why I tried to
bring
>you to this decision, but you were adamant. (:-))

Hm, they keep saying that... ;)

Also have in mind that I may fail in digesting everything you say...
I'm both an Ada beginner and increasingly stressed... I've spent too
much time on this problem by now. But you've been of GREAT help!




  reply	other threads:[~2005-01-05 12:01 UTC|newest]

Thread overview: 31+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2004-12-22 13:49 OO problem: Performing actions on messages (very long, sorry) per
2004-12-22 15:17 ` Dmitry A. Kazakov
2004-12-22 16:28 ` Martin Krischik
2004-12-22 17:42   ` per
2004-12-22 18:16     ` Martin Krischik
2004-12-22 19:54     ` Dmitry A. Kazakov
2005-01-03 12:37       ` per
2005-01-03 14:14         ` Dmitry A. Kazakov
2005-01-04 12:05           ` per
2005-01-04 13:30             ` Dmitry A. Kazakov
2005-01-04 15:21               ` per
2005-01-04 17:47                 ` Dmitry A. Kazakov
2005-01-05 12:01                   ` per [this message]
2005-01-05 13:23                     ` Dmitry A. Kazakov
2005-01-05 15:59                       ` per
2005-01-05 20:44                         ` Dmitry A. Kazakov
2005-01-10  8:42                           ` per
2005-01-10 14:22                             ` Dmitry A. Kazakov
2005-01-10 16:24                               ` per
2005-01-10 19:09                                 ` Dmitry A. Kazakov
2005-01-11  9:06                                   ` per
2004-12-22 17:46   ` per
2004-12-22 18:02     ` Martin Krischik
2005-01-03 10:05       ` per
2004-12-22 18:35     ` u_int32_t
2004-12-22 18:38       ` u_int32_t
2004-12-24 18:52 ` Nick Roberts
2005-01-03 16:59   ` per
2005-01-10 12:10   ` per
2005-01-10 13:49     ` Marius Amado Alves
2005-01-10 21:54 ` Simon Wright
replies disabled

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