built-in types inside of a union
Ali Çehreli via Digitalmars-d-learn
digitalmars-d-learn at puremagic.com
Wed Jul 13 07:22:29 PDT 2016
On 07/13/2016 07:01 AM, Adam D. Ruppe wrote:
> On Wednesday, 13 July 2016 at 12:28:57 UTC, zodd wrote:
>> This code works as I expected but I'm unsure that it's correct.
>
> Yes, your code is legal.
>
> What isn't legal is using some type that isn't there at runtime, like
>
> union A {
> int[] a;
> char[] b;
> }
>
> A u;
>
> u.a = [1,2];
>
> u.b.length
>
>
> The compiler will let you do it, but being a union, it will show length
> == 1 because it was set to an int[], but that's not really correct for a
> char[].
>
>
> But the way you did it, initializing to the proper type before accessing
> it, is allowed.
Although, in some cases even that assignment operation can do the wrong
thing. In general, the left-hand side of the assignment does not hold
the invariants of that user-defined type:
import std.stdio;
struct S {
string fileName;
S opAssign(S) const {
writefln("deleting %s", fileName); // <-- Oops.
return this;
}
}
union U {
S s;
string file;
}
void main() {
U u;
u.file = "important_file.txt";
// This assignment is executed on an S that is not properly
// initialized. The operation deletes an unrelated file.
u.s = S.init;
}
Of course, users of unions must understand how bits of different types
are shared and how that can cause trouble.
Ali
More information about the Digitalmars-d-learn
mailing list