Why is it difficult to reference arrays in structs?
mipri
mipri at minimaltype.com
Thu Oct 3 04:54:36 UTC 2019
On Thursday, 3 October 2019 at 04:32:52 UTC, Brett wrote:
> struct Y { double q; }
> struct X { Y[] a; }
>
> X x;
>
> auto r = x.a;
>
> r is not a reference?!?!
Arrays are (ptr,length) pairs. r is a copy of them:
#! /usr/bin/env rdmd
import std.stdio;
struct X { int[] a; }
void main() {
auto test = X([0]);
test.a.reserve(10); // for later
auto r = test.a;
writeln(test.a.ptr == r.ptr); // true
writeln(test.a.length == r.length); // true
}
Mutate it and they're still using the same ptr:
r ~= [1];
writeln(test.a.ptr == r.ptr); // true
writeln(test.a.length == r.length); // false
But r is still a copy of the ptr,length pair, and
its length is updated separately.
Consider:
#! /usr/bin/env rdmd
import std.stdio;
struct X { int[] a; }
void main() {
X test;
test.a.reserve(3);
auto a = test.a;
a ~= [1, 2, 3];
auto r = test.a.ptr[0..3];
writeln(r); // output: [1, 2, 3]
}
I have to slice the ptr directly as array operations are aware
of all this. Consider:
#! /usr/bin/env rdmd
import std.stdio;
struct X { int[] a; }
void main() {
X test;
test.a.reserve(3);
auto a = test.a;
a ~= [1, 2, 3];
test.a.length = 3;
writeln(test.a); // [0,0,0]
writeln(a); // [1,2,3]
}
What you can do copy the (ptr,length) pair, do what you want with
it, and then assign it back to the struct. Don't worry about
tricky
stuff.
> auto r = &x.a;
>
> Now r is a reference, great!.
look at it:
writeln(typeid(a)); // output: int[]*
It's a pointer to an int[]. It behaves like a pointer.
> I want to have a slice of an array that I can append to as a
> sort of temporary and have it append to the main array(the end
> of the slice always is the end of the main array)..
>
> I've tried assumeSafeAppend but it does nothing to help.
Learning D goes into tons of detail about slices and appending to
copies and when you'd want assumeSafeAppend and so on.
More information about the Digitalmars-d-learn
mailing list