Troubles creating templated inout objects

Steven Schveighoffer schveiguy at yahoo.com
Tue Jul 10 18:01:59 UTC 2018


On 7/10/18 10:34 AM, Timoses wrote:
> How do I create an inout object with template parameters?
> 
> Take following code:
> 
>      import std.stdio;
>      import std.traits;
> 
>      struct S
>      {
>          int[] arr;
>      }
> 
>      interface I
>      {
>          inout(I) opIndex(size_t idx) inout;
>      }
> 
>      class Test(T) : I
>      {
>                  // Error: variable 
> `onlineapp.Test!(inout(int)[]).Test.member` only parameters or stack 
> based variables can be inout
>          T member;
> 
>          this(inout T mem) inout
>          {
>              this.member = mem;
>          }
> 
>          inout(Test!T) get() inout
>          {
>              return new inout Test!(Unqual!(typeof(member)))(member);
>          }
> 
>          inout(I) opIndex(size_t idx) inout
>          {
>              switch (idx)
>              static foreach (index, t; T.tupleof)
>              {
>                  case index:
>                                          // Error: template instance 
> `onlineapp.Test!(inout(int)[])` error instantiating
>                      return new inout
>                          Test!(Unqual!(typeof(this.member.tupleof[index])))
>                                      (this.member.tupleof[index]);
>                  default:
>                      return null;
>              }
>          }
>      }
> 
> 
>      unittest
>      {
>          auto s = S([1,2,3]);
>          auto t = new const Test!S(s);
>      }
> 
> 
> `Unqual` in this case just turns `inout(int[])` into `inout(int)[]`, 
> which is why it complains. That's a side effect of this example, however 
> the main question is how one would go about achieving something like 
> this idiomatically?
> 
> I would like to return a new object and that object should have the same 
> mutability as the one creating it.

You are overthinking :) inout typically is much easier than you expect, 
until you need to create temporary structs or types with inout members, 
then it becomes problematic.

https://run.dlang.io/is/kosYuC

I had to put in a static if, because your function doesn't work once you 
get down to the array type. See the // fixme comment.

-Steve


More information about the Digitalmars-d-learn mailing list