Unexpected aliasing
Antonio Corbi
antonio at ggmail.com
Mon Nov 11 20:05:11 UTC 2019
On Monday, 11 November 2019 at 19:17:37 UTC, Bastiaan Veelo wrote:
> Recently I got my first surprise with our use of D. The symptom
> was that two local variables in two different functions
> appeared to be sharing data.
>
> A simplified example is shown below (the original was machine
> translated from Pascal and involved templates and various
> levels of indirection). What I did not know is that the initial
> value of struct members is a compile time feature, apparently.
> What I suspect is happening is that the array lives in the
> static data segment (or is created in the module constructor?)
> and that the slices inside arr1 and arr2 get initialised to
> point to that same array.
>
> I could use some help in rewriting the code below so that arr1
> and arr2 each have their own data; ideally with minimal changes
> so that I can make the transcompiler do the right thing.
>
> Thanks!
> Bastiaan.
>
> void main()
> {
> import std.stdio;
>
> WrapIntegerArray arr1;
> arr1[0] = 42;
>
> WrapIntegerArray arr2;
>
> writeln(arr2[0]); // 42, not 0.
> writeln("arr1.wrap.arr.ptr = ", arr1.wrap.arr.ptr);
> writeln("arr2.wrap.arr.ptr = ", arr2.wrap.arr.ptr); //
> identical
> assert(arr2[0] == 0); // fails
> }
>
> struct IntegerArray
> {
> int[] arr;
> alias arr this;
> this(int l)
> {
> arr = new int[l];
> }
> }
>
> struct WrapIntegerArray
> {
> auto wrap = IntegerArray(5); // This is CTFE! :-(
> alias wrap this;
> }
Defining and using a constructor for WrapIntegerArray seems to
work:
void main()
{
import std.stdio;
WrapIntegerArray arr1 = WrapIntegerArray(5);
arr1[0] = 42;
WrapIntegerArray arr2 = WrapIntegerArray(5);
writeln(arr2[0]); // 42, not 0.
writeln("arr1.wrap.arr.ptr = ", arr1.wrap.arr.ptr);
writeln("arr2.wrap.arr.ptr = ", arr2.wrap.arr.ptr); // identical
assert(arr2[0] == 0); // fails
}
struct IntegerArray
{
int[] arr;
alias arr this;
this(int l)
{
arr = new int[l];
}
}
struct WrapIntegerArray
{
this (int v) {
wrap = IntegerArray(5);
}
IntegerArray wrap;
alias wrap this;
}
Hope this helps.
Antonio
More information about the Digitalmars-d-learn
mailing list