On Monday, 2 October 2023 at 20:42:14 UTC, Paul Backus wrote:
On Monday, 2 October 2023 at 20:34:11 UTC, Salih Dincer wrote:
In an old version (for example, v2.0.83), the code you implemented in the places where Slice is written above works as desired. In the most current versions, the parameterized opIndexAssign(T value) gives the error:

onlineapp.d(51): Error: function `onlineapp.Matrix!double.Matrix.opIndexAssign(double value)` is not callable using argument types `(double, ulong)`
onlineapp.d(51):        expected 1 argument(s), not 2

**Source:** https://run.dlang.io/is/TPAg5m

I don't know what's wrong in your example but this works for me:

```d
struct S
{
    void opIndexAssign(int value)
    {
        import std.stdio;
        writeln("assigned ", value);
    }
}

void main()
{
    S s;
    s[] = 7;
}
```

So in the example linked by Salih, the `opIndex` returns a ref, which is a valid mechanism to properly do `a[0] = val;`. However, since `opIndexAssign` exists, the compiler expects that to be used instead.

Essentially, by naming the slice assign the same operator as index assign, you have eliminated the possibility for ref assignment via indexing.

Now, you can define a further `opIndexAssign(T val, size_t idx)`. However, now you lose capabilities like `a[0]++`, which I don't think has a possibility of implementing using an `opIndex` operator, and it would be pretty ugly if you had to.

This seems like a design flaw in the `opIndex` overloading changes. I would stick with `opSliceAssign` if faced with this problem (glad it still works!)

It could also be considered a bug but I don't know the overload implications.

-Steve

Reply via email to