Jump to page: 1 2
Thread overview
Getting a working example of opIndexAssign using opSlice ... have troubles ...
Aug 15, 2021
james.p.leblanc
Aug 15, 2021
Bastiaan Veelo
Aug 15, 2021
james.p.leblanc
Aug 15, 2021
james.p.leblanc
Aug 15, 2021
ag0aep6g
Aug 15, 2021
russhy
Aug 16, 2021
Tejas
Aug 16, 2021
james.p.leblanc
Aug 16, 2021
Tejas
Aug 16, 2021
james.p.leblanc
Aug 16, 2021
Tejas
Aug 16, 2021
james.p.leblanc
Aug 16, 2021
Tejas
Aug 16, 2021
Alexandru Ermicioi
Aug 16, 2021
james.p.leblanc
August 15, 2021

Greetings,

I have been trying to get a working example of slice assignment operator
overloading ... and am befuddled. From the spec (section 20.6.2), the
code below appears:

struct A
{
    int opIndexAssign(int v);  // overloads a[] = v
    int opIndexAssign(int v, size_t[2] x);  // overloads a[i .. j] = v
    int[2] opSlice(size_t x, size_t y);     // overloads i .. j
}

void test()
{
    A a;
    int v;

    a[] = v;  // same as a.opIndexAssign(v);
    a[3..4] = v;  // same as a.opIndexAssign(v, a.opSlice(3,4));
}

I have hacked at this trying to get a simple working example. Could
anyone guide me here please?

Best Regards,
James

August 15, 2021

On Sunday, 15 August 2021 at 20:41:51 UTC, james.p.leblanc wrote:

>
struct A
{
    int opIndexAssign(int v);  // overloads a[] = v
    int opIndexAssign(int v, size_t[2] x);  // overloads a[i .. j] = v
    int[2] opSlice(size_t x, size_t y);     // overloads i .. j
}

void test()
{
    A a;
    int v;

    a[] = v;  // same as a.opIndexAssign(v);
    a[3..4] = v;  // same as a.opIndexAssign(v, a.opSlice(3,4));
}

I have hacked at this trying to get a simple working example.

Not sure if this does enough of what you’re looking for, but this covers the minimal steps to get it working: https://run.dlang.io/is/m5svQ2


import std;

struct A
{
    int opIndexAssign(int v) // overloads a[] = v
    {
        writeln(__FUNCTION__);
        return 42;
    }
    int opIndexAssign(int vh, size_t[2] x)  // overloads a[i .. j] = v
    {
        writeln(__FUNCTION__);
        return 43;
    }
    int[2] opSlice(size_t x, size_t y)     // overloads i .. j
    {
        writeln(__FUNCTION__);
        return [44, 45];
    }
}

void main()
{
    A a;
    int v;

    a[] = v;  // same as a.opIndexAssign(v);
    a[3..4] = v;  // same as a.opIndexAssign(v, a.opSlice(3,4));
}

— Bastiaan.

August 15, 2021

On Sunday, 15 August 2021 at 20:41:51 UTC, james.p.leblanc wrote:

>

I have been trying to get a working example of slice assignment operator
overloading ... and am befuddled. From the spec (section 20.6.2), the
code below appears:

struct A
{
    int opIndexAssign(int v);  // overloads a[] = v
    int opIndexAssign(int v, size_t[2] x);  // overloads a[i .. j] = v
    int[2] opSlice(size_t x, size_t y);     // overloads i .. j
}

void test()
{
    A a;
    int v;

    a[] = v;  // same as a.opIndexAssign(v);
    a[3..4] = v;  // same as a.opIndexAssign(v, a.opSlice(3,4));
}

I have no experience with this, but from a cursory look it seems that that example is wrong.

For starters, the type of opIndexAssign's second parameter must match the return type of opSlice. This is easily fixed, but the code still doesn't work.

Further down on the spec page [1], there is this little table:

op rewrite
arr[1, 2..3, 4] = c arr.opIndexAssign(c, 1, arr.opSlice!1(2, 3), 4)
arr[2, 3..4] += c arr.opIndexOpAssign!"+"(c, 2, arr.opSlice!1(2, 3))

Note the !1 on opSlice. So you need to make opSlice a template with an integer parameter.

Working example:

import std.stdio;

struct A
{
    int opIndexAssign(int v, size_t[2] x)
    {
        writeln("opIndexAssign: ", v, ", ", x);
        return v;
    }
    size_t[2] opSlice(size_t i)(size_t x, size_t y)
    {
        return [x, y];
    }
}

void main()
{
    A a;
    int v = 42;
    a[3..4] = v; /* Prints "opIndexAssign: 42, [3, 4]". */
}

[1] https://dlang.org/spec/operatoroverloading.html#slice

August 15, 2021

There is an example here:

http://www.rosettacode.org/wiki/Multi-dimensional_array#D

Look at the Matrix struct

August 15, 2021

On Sunday, 15 August 2021 at 21:15:02 UTC, Bastiaan Veelo wrote:

>

On Sunday, 15 August 2021 at 20:41:51 UTC, james.p.leblanc

>

— Bastiaan.

Bastiaan,

Thanks kindly for your response!

Unfortunately, I do not see what the program does. I mean A is a structure
that has only functions. So, how are any elements of this being set to
the value of v?

I tried extending the code mentioned by adding a member array, but no
luck.

I often have difficulties to understand the notations used in the spec,
and only sometimes can I extend them to working examples.

Would it be possible to add the last couple of details regarding
an array member? I attempted but the values always remain zero
even when I set v=4.

import std;

struct A
{
   int[5] a;
   int opIndexAssign(int v) // overloads a[] = v
   {
      writeln(__FUNCTION__);
      return 42;
   }
   int opIndexAssign(int vh, size_t[2] x)  // overloads a[i .. j] = v
   {
      writeln(__FUNCTION__);
      return 43;
   }
   int[2] opSlice(size_t x, size_t y)     // overloads i .. j
   {
      writeln(__FUNCTION__);
      return [44, 45];
   }
}

void main()
{
   A a;
   int v=4;
   writeln(a);

   a[] = v;  // same as a.opIndexAssign(v);
   writeln(a);
   a[3..4] = v;  // same as a.opIndexAssign(v, a.opSlice(3,4));
   writeln(a);
}

Thanks once again,
James

August 15, 2021

On Sunday, 15 August 2021 at 21:28:53 UTC, james.p.leblanc wrote:

>

On Sunday, 15 August 2021 at 21:15:02 UTC, Bastiaan Veelo wrote:

>

On Sunday, 15 August 2021 at 20:41:51 UTC, james.p.leblanc

>

— Bastiaan.

Bastiaan,

Thanks once again,
James

On Sunday, 15 August 2021 at 21:28:53 UTC, james.p.leblanc wrote:

Okay! Great! Thanks everyone Bastiaan, ag0aep6g, and russhy ...
I see more replies come in while I was typing.

There is some excellent information here that I
need to digest. I believe that I have what I need.

This group has been great!

BR,
James

August 16, 2021

On Sunday, 15 August 2021 at 20:41:51 UTC, james.p.leblanc wrote:

>

Greetings,

I have been trying to get a working example of slice assignment operator
overloading ... and am befuddled. From the spec (section 20.6.2), the
code below appears:

struct A
{
    int opIndexAssign(int v);  // overloads a[] = v
    int opIndexAssign(int v, size_t[2] x);  // overloads a[i .. j] = v
    int[2] opSlice(size_t x, size_t y);     // overloads i .. j
}

void test()
{
    A a;
    int v;

    a[] = v;  // same as a.opIndexAssign(v);
    a[3..4] = v;  // same as a.opIndexAssign(v, a.opSlice(3,4));
}

I have hacked at this trying to get a simple working example. Could
anyone guide me here please?

Best Regards,
James

If you're finding the spec too hard, please try Ali's book. I'm sharing the part on operator overloading below:

http://ddili.org/ders/d.en/operator_overloading.html

Please ping if you still have problems; I'll then write a full program.

August 16, 2021

On Monday, 16 August 2021 at 05:26:00 UTC, Tejas wrote:

>

If you're finding the spec too hard, please try Ali's book. I'm sharing the part on operator overloading below:

http://ddili.org/ders/d.en/operator_overloading.html

Please ping if you still have problems; I'll then write a full program.

Hej Tejas!

Thanks for your message. I have it working now. Yes, Ali's book is
a tremendously good reference. But, I had trouble digging out
the "magic sauce" from the pages to get this working.

I was able to find the sauce in a forum post by Adam Ruppe (his book is also
an excellent place for ideas and code).

With "opCast", my difficulty was the description of the type I wish to cast
to uses a colon ":".

Here is the line that allows it to function as desired:

>> T[] opCast(T : T[])(){... }

Best Regards,
jpl

August 16, 2021

On Monday, 16 August 2021 at 06:12:42 UTC, james.p.leblanc wrote:

>

On Monday, 16 August 2021 at 05:26:00 UTC, Tejas wrote:

>

If you're finding the spec too hard, please try Ali's book. I'm sharing the part on operator overloading below:

http://ddili.org/ders/d.en/operator_overloading.html

Please ping if you still have problems; I'll then write a full program.

Hej Tejas!

Thanks for your message. I have it working now. Yes, Ali's book is
a tremendously good reference. But, I had trouble digging out
the "magic sauce" from the pages to get this working.

I was able to find the sauce in a forum post by Adam Ruppe (his book is also
an excellent place for ideas and code).

With "opCast", my difficulty was the description of the type I wish to cast
to uses a colon ":".

Here is the line that allows it to function as desired:

>> T[] opCast(T : T[])(){... }

Best Regards,
jpl

Maybe just write T[] in code rather than making it happen via the colon?

I also have similar troubles, removing the default value always helped me.

Can you show the code where you're trying to apply this?

August 16, 2021
On Monday, 16 August 2021 at 06:20:11 UTC, Tejas wrote:

> Maybe just write `T[]` in code rather than making it happen via the colon?
>
> I also have similar troubles, removing the default value always helped me.
>
> Can you show the code where you're trying to apply this?

Hej Tejas,

Sure, here is the code snippet, it resides within a struct
along with various operator overloads.

To be honest, I am not exactly sure what is happening here. I
am unfamiliar with the "(T : T[])" syntax ... need to read
up a bit on that. (However, not so eary searching for a ":")

BR,
jpl


// --- cast overloading -------------------------------------------
// T[] opCast(T : T[])(){     // this works
   T[] opCast(T[])(){ // yields: "Error: identifier expected for template value param"
      T[] x;
      x.length = this.length;
      for( int i = 0 ; i< this.length ; i++){
         x[i] = this.ptr[i];
      }
      return x;
   }



« First   ‹ Prev
1 2