www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.learn - ref parameter qualifier and static arrays

reply "Paul" <paul example.com> writes:
Is it possible to call a function like this...

void foo(ref int[] anArray)

...with slices of static arrays? I thought I might be able to use 
[0..$-1] but to no avail - I get an error like this (which is 
confusing!):

(ref int[] anArray) is not callable using argument types (int[])

I've modified the function declaration and used .ptr when calling 
it but it seems like a retrograde step for a modern language - 
although I suppose ref is pretty much the same thing.

In practice I'm using arrays of structs (which are of various 
fixed sizes and known at compile time) that are currently global 
in scope - something that I'd like to avoid.

I suppose I could just ask, what is the 'best' way to give access 
to variously sized static arrays between different modules?
Sep 09 2015
next sibling parent "anonymous" <a b.cd> writes:
On Wednesday, 9 September 2015 at 20:18:57 UTC, Paul wrote:
 Is it possible to call a function like this...

 void foo(ref int[] anArray)

 ...with slices of static arrays? I thought I might be able to 
 use [0..$-1] but to no avail - I get an error like this (which 
 is confusing!):
Note that the upper bound of the slice is exclusive - [0..$-1] is not the whole array but everthing except the last entry. To slice the whole array, you can use [0..$] or just write int[42] a; auto b = a[];
 (ref int[] anArray) is not callable using argument types (int[])

 I've modified the function declaration and used .ptr when 
 calling it but it seems like a retrograde step for a modern 
 language - although I suppose ref is pretty much the same thing.

 In practice I'm using arrays of structs (which are of various 
 fixed sizes and known at compile time) that are currently 
 global in scope - something that I'd like to avoid.

 I suppose I could just ask, what is the 'best' way to give 
 access to variously sized static arrays between different 
 modules?
It is impossible to pass a rvalue as a reference (intended behaviour, afaik it is causes problems if the reference escapes from foo and outlasts the rvalue). There is a bug report about the strange error message somewhere in the bug tracker. Some time ago someone announced to implement passing rvalue as reference but it seems the PR was not merged for dmd 2.068. Workaround: use a temporary variable. instead of int[42] a; foo(a[]); write int[42] a; auto tmp = a[]; foo(tmp);
Sep 09 2015
prev sibling parent reply anonymous <anonymous example.com> writes:
On Wednesday 09 September 2015 22:18, Paul wrote:

 
 Is it possible to call a function like this...
 
 void foo(ref int[] anArray)
 
 ...with slices of static arrays? I thought I might be able to use 
 [0..$-1] but to no avail - I get an error like this (which is 
 confusing!):
 
 (ref int[] anArray) is not callable using argument types (int[])
Slice expressions are not lvalues (can't take their addresses), so you can't pass them in ref parameters. You can store the slice in a variable and pass that: ---- void f(ref int[] x) {} int[3] a; version(none) f(a[]); /* Nope, a[] is not an lvalue. */ int[] s = a[]; f(s); /* Ok, s is an lvalue. */ ---- But if you want to pass slice expressions, then you probably don't need that ref. When you pass a slice (without ref), what's actually passed is a pointer and length. The contents are not copied. That means, when you alter an array element, the change will be done the original, even without ref: ---- void f(int[] x) {x[0] = 1;} int[3] a = [0, 0, 0]; f(a[]); assert(a[0] == 1); /* passes */ ---- ref would allow you to resize the original dynamic array: ---- void f(ref int[] x) {x ~= 4;} int[] a = [1, 2, 3]; f(a); assert(a.length == 4); /* passes */ ---- But there's no point in doing that to temporaries like slice expressions.
Sep 09 2015
parent "Paul" <paul example.com> writes:
On Wednesday, 9 September 2015 at 20:35:53 UTC, anonymous wrote:

 When you pass a slice (without ref), what's actually passed is 
 a pointer and length. The contents are not copied. That means, 
 when you alter an array element, the change will be done the 
 original, even without ref:
Thanks both. I see, temporary variable and no ref will do the job and I suppose it's better than just using a global...
Sep 10 2015