Thread overview
is ref inout redundant in: ref inout(T) opIndex(size_t index)
Jun 19, 2023
mw
Jun 21, 2023
Nick Treleaven
June 19, 2023

Hi, I just saw this line:

https://github.com/dlang/dmd/blob/master/druntime/src/core/stdcpp/vector.d#LL66C5-L66C39

66:    ref inout(T) opIndex(size_t index) inout pure nothrow @safe @nogc       { return as_array[index]; }

I'm wondering if the ref and inout redundant here? They both mean the same thing? in C++ terms both return the reference of the i-th element? so only one of them should be enough?

If not, can someone help to explain the difference? the following 4 return types:

  1. ref T alone
  2. inout T alone
  3. ref inout(T)
  4. inout ref(T)

BTW, what does the second inout before pure do? it's also redundant?

Thanks.

June 19, 2023

On 6/19/23 2:19 PM, mw wrote:

>

Hi, I just saw this line:

https://github.com/dlang/dmd/blob/master/druntime/src/core/stdcpp/vector.d#LL66C5-L66C39

66:    ref inout(T) opIndex(size_t index) inout pure nothrow @safe @nogc       { return as_array[index]; }

I'm wondering if the ref and inout redundant here? They both mean the same thing? in C++ terms both return the reference of the i-th element? so only one of them should be enough?

No, they do not both mean the same thing. inout is a form of mutability that is unique to D. It does not mean the same as ref like other languages (or even D1).

What inout does is forward the mutability of the parameter to the return type.

>

If not, can someone help to explain the difference? the following 4 return types:

  1. ref T alone

a reference to a T.

>
  1. inout T alone

An inout T passed by value. Sorry for the recursive definition, but inout is kinda unique with D.

>
  1. ref inout(T)

A reference to an inout T.

>
  1. inout ref(T)

I'm not sure that's valid. ref is a storage class, not a type modifier.

>

BTW, what does the second inout before pure do? it's also redundant?

This is the qualifier put onto the this parameter (i.e. the vector in this case).

Because of this, you get the mutability of the parameter forwarded to the return type.

const vector!int c;
immutable vector!int i;
vector!int m;

static assert(is(typeof(c[0]) == const(int)));
static assert(is(typeof(i[0]) == immutable(int)));
static assert(is(typeof(m[0]) == int));

I gave a presentation on const/inout, which you might find helpful.

https://dconf.org/2016/talks/schveighoffer.html

-Steve

June 21, 2023

On Monday, 19 June 2023 at 18:19:18 UTC, mw wrote:

>
  1. inout T alone

Steve covered everything, though you might also like to read the inout spec:
https://dlang.org/spec/const3.html#inout