* Conditional holder for a type with unknown discriminant
@ 2012-10-27 2:50 Yannick Duchêne (Hibou57)
2012-10-27 9:15 ` AdaMagica
` (2 more replies)
0 siblings, 3 replies; 6+ messages in thread
From: Yannick Duchêne (Hibou57) @ 2012-10-27 2:50 UTC (permalink / raw)
Hi Ada hackers (lol, does this word can comes Ada?),
Not the first time I face this question, just that it came back to me.
The matter: a conditional holder à‑la SML is an idiom easily expressed in
Ada, except when the object to be wrapped also has to have an unknown
discriminant.
Example:
type E_Type is private;
type W_Type
(Is_Null : Boolean)
is record
case Is_Null is
when True => null;
when False => E : E_Type;
end case;
end record;
function F return W_Type;
`W_Type` is the result of a request returning an element of type `E_Type`,
which may return nothing.
Pros: avoid testing of condition dissociated from the result.
Cons: troubles when `E_Type` has unknown discriminant.
type E_Type (<>) is private;
type W_Type
(Is_Null : Boolean)
is record
case Is_Null is
when True => null;
when False => E : E_Type;
end case;
end record;
function F return W_Type;
Oops, unconstrained subtype in record definition.
You may give default values to discriminant, but no there may be no well
good enough defaults, and you may also want the client side to not create
an instance of `E_Type`, which would not be meaningful.
I tried to have this:
type E_Type (<>) is private;
type W_Type
(Is_Null : Boolean)
is tagged record
case Is_Null is
when True => null;
when False => E : not null access E_Type;
end case;
end record;
function F return W_Type'Class;
Then, a type derived from `W_Type` extends it with an added `E_Type`
aliased member… I bet you guess I would like to be able to assign `E` a
reference to that member, but that's a no way: compiling the specification
is OK, but compiling any implementation fails.
Should I give up with this and use a precondition instead?
What a pity we can't have a structure referencing it's own component. That
would be perfectly valid from an access point of view, but we can't use a
declaration before it's terminated, so access discriminant does not help
here, as what is required, is an access to an inner element:
X : X_Type
(...
E_Object => (...),
E => X.E_Object'Access); -- Fails
It happens I miss we could do that (providing `X_Type` would be a limited
type, of course).
--
“Syntactic sugar causes cancer of the semi-colons.” [1]
“Structured Programming supports the law of the excluded muddle.” [1]
[1]: Epigrams on Programming — Alan J. — P. Yale University
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Conditional holder for a type with unknown discriminant
2012-10-27 2:50 Conditional holder for a type with unknown discriminant Yannick Duchêne (Hibou57)
@ 2012-10-27 9:15 ` AdaMagica
2012-10-27 12:03 ` Yannick Duchêne (Hibou57)
2012-10-27 17:17 ` AdaMagica
2012-10-27 19:14 ` gautier_niouzes
2 siblings, 1 reply; 6+ messages in thread
From: AdaMagica @ 2012-10-27 9:15 UTC (permalink / raw)
A.18.18 Indefinite Holders might help.
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Conditional holder for a type with unknown discriminant
2012-10-27 9:15 ` AdaMagica
@ 2012-10-27 12:03 ` Yannick Duchêne (Hibou57)
0 siblings, 0 replies; 6+ messages in thread
From: Yannick Duchêne (Hibou57) @ 2012-10-27 12:03 UTC (permalink / raw)
Le Sat, 27 Oct 2012 11:15:30 +0200, AdaMagica
<christ-usch.grein@t-online.de> a écrit:
> A.18.18 Indefinite Holders might help.
I had a look back at it, after your suggestion, but that will not do the
trick (except for one thing).
Let me explain what I'm looking for with the record construct explain in
the initial post. First, an example in Ada (again), then, a similar thing
in SML, with comments to compare both.
type S is (Is_Null, Has_Item);
type R (D : S)
is record
case S is
when Is_Null => null;
when Has_Item => I : T;
end case;
end record;
which could be used this way:
Y : R := F (...);
case R.S is
when Is_Null =>
-- Do nothing which could
-- attempt to access `R.I`.
null;
when Has_Item =>
P (R.I);
-- Do whatever you want
-- on `R.I`.
end case;
Now, the SML way, which looks very close, but which I can reach only
imperfectly in Ada (see comments below):
datatype R =
Is_Null
| Has_Item of T;
which could be used this way:
let
y = f (...)
in
case y of
Is_Null =>
-- What you want,
-- but no access to I.
Has_Item (i) =>
-- What you want of I.
end;
Now the comparison is that in the Ada case, you can still attempt to
access `R.I` in the `Is_Null` branch… you will obviously get an error at
run‑time, but it will compile (may be with compiler warnings, but it will
compile). In the SML case, you just have simply no way to erroneously
access `i`, that impossible, because unless SML matched the structure `y`
to the pattern `Has_Item (y)`, then `y` simply does not exist and is not
accessible at all. Anyway, I still wanted to do the best with Ada to match
this construct, and this works, except when the type of `I` in this
example, has an unknown discriminant.
But I think there is an other option, more close to the SML semantic,
while less close semantically, which is to use a call‑back subprogram to
be applied on `I`. That way, you the same as with SML: unless `I` was
really passed to you, you have strictly no way to access it, that's
absolute safety.
Has a side note, this may be an argument for active iterators over passive
iterators. But that does not work well for all cases. That's OK as long as
the operations to be applied on each iterated item is the same and, more
importantly, always occurs in the same context, otherwise, things become
complicated to setup, and the passive iterators looks better in such
cases; but with the drawback it has.
Has another side note, the way SML do things (which work well) for request
function/iterator, may suggest the test should be done on the return
result, instead of on the iterator.
I also have some though about compared efficiency of the call‑back method
with an active iterator vs the passive iterator, but I'm not sure it's
worth to expose.
Well, so far, I think I will go for passive with call back for iterators
and request functions. Will see if that still looks OK after some time
doing things with it.
--
“Syntactic sugar causes cancer of the semi-colons.” [1]
“Structured Programming supports the law of the excluded muddle.” [1]
[1]: Epigrams on Programming — Alan J. — P. Yale University
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Conditional holder for a type with unknown discriminant
2012-10-27 2:50 Conditional holder for a type with unknown discriminant Yannick Duchêne (Hibou57)
2012-10-27 9:15 ` AdaMagica
@ 2012-10-27 17:17 ` AdaMagica
2012-10-27 19:14 ` gautier_niouzes
2 siblings, 0 replies; 6+ messages in thread
From: AdaMagica @ 2012-10-27 17:17 UTC (permalink / raw)
Can't see why this shouldn't do the trick:
package Owl_Holder is new Ada.Containers.Indefinite_Holders (T);
use Owl_Holder;
type R (Has_Item: Boolean) is record
case Has_Item is
when False => null;
when True => I: Holder;
end case;
end record;
Y: R := F (...);
case Y.Has_Item is
when False => null; -- Do nothing
when True => P (Y.I.Element); -- Do whatever you want
P (Element (Y.I); -- ditto
P (Y.I.Reference); -- ditto using Ada 2012 reference type
Y.I.Reference := New_Item; -- via reference type or
Y.I.Replace_Element (New_Item); -- in traditional way
end case;
(Haven't compiled, but you get the idea:-)
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Conditional holder for a type with unknown discriminant
2012-10-27 2:50 Conditional holder for a type with unknown discriminant Yannick Duchêne (Hibou57)
2012-10-27 9:15 ` AdaMagica
2012-10-27 17:17 ` AdaMagica
@ 2012-10-27 19:14 ` gautier_niouzes
2012-10-29 7:22 ` Yannick Duchêne (Hibou57)
2 siblings, 1 reply; 6+ messages in thread
From: gautier_niouzes @ 2012-10-27 19:14 UTC (permalink / raw)
> Hi Ada hackers (lol, does this word can comes Ada?),
It fits! The best tool for cracking codes, tampering executables, etc. (biased opinion).
An embryonic project of mine is called HAC - the Hacker's Ada Compiler - based on SmallAda. Never reached the "barely working" status...
http://coding.derkeiler.com/Archive/Ada/comp.lang.ada/2009-03/msg00170.html
^ permalink raw reply [flat|nested] 6+ messages in thread
* Re: Conditional holder for a type with unknown discriminant
2012-10-27 19:14 ` gautier_niouzes
@ 2012-10-29 7:22 ` Yannick Duchêne (Hibou57)
0 siblings, 0 replies; 6+ messages in thread
From: Yannick Duchêne (Hibou57) @ 2012-10-29 7:22 UTC (permalink / raw)
Le Sat, 27 Oct 2012 21:14:16 +0200, <gautier_niouzes@hotmail.com> a écrit:
>> Hi Ada hackers (lol, does this word can comes Ada?),
>
> It fits! The best tool for cracking codes, tampering executables, etc.
> (biased opinion).
>
> An embryonic project of mine is called HAC - the Hacker's Ada Compiler -
> based on SmallAda. Never reached the "barely working" status...
>
> http://coding.derkeiler.com/Archive/Ada/comp.lang.ada/2009-03/msg00170.html
I see, so as they even gone beyond that, we should rename AdaCore, the Big
Hackers Company.
--
“Syntactic sugar causes cancer of the semi-colons.” [1]
“Structured Programming supports the law of the excluded muddle.” [1]
[1]: Epigrams on Programming — Alan J. — P. Yale University
^ permalink raw reply [flat|nested] 6+ messages in thread
end of thread, other threads:[~2012-10-29 7:22 UTC | newest]
Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2012-10-27 2:50 Conditional holder for a type with unknown discriminant Yannick Duchêne (Hibou57)
2012-10-27 9:15 ` AdaMagica
2012-10-27 12:03 ` Yannick Duchêne (Hibou57)
2012-10-27 17:17 ` AdaMagica
2012-10-27 19:14 ` gautier_niouzes
2012-10-29 7:22 ` Yannick Duchêne (Hibou57)
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox