On Tue, 07 Jul 2015 11:09:52 +0000, Peter wrote:

Any ideas about what's happening?

yes. there is code in "arrayop.c" that tells:

// Built-in array ops should be @trusted, pure, nothrow and nogc StorageClass stc = STCtrusted | STCpure | STCnothrow | STCnogc;

under the hoods compiler rewrites `f[] = c[]+d[];` to this:

_arraySliceSliceAddSliceAssign_S3z007Vector3 extern (C) Vector3[]
  (Vector3[] p2, const Vector3[] p1, const Vector3[] p0)
  pure nothrow @nogc @trusted
  {
    foreach (p; 0u .. p2.length) {
      p2[p] = cast(Vector3)(p0[p] + p1[p]);
    }
    return p2;
  }

  _arraySliceSliceAddSliceAssign_S3z007Vector3(f, c, d);

do you see the gotcha? if you uncomment postblit or assigns, this build function fails to compile, as that operations aren't "pure nothrow @nogc @trusted", and they will be used for either assign or postblitting.

the same will happen if you add anything to your `opBinary` which make it unpure/@system (like `writeln`, for example). i.e.

  Vector3 opBinary(string op : "+") (in Vector3 rhs) const {
    import std.stdio; writeln("opBinary"); // (1)
    Vector3 result;
    result.vdata[] = this.vdata[] + rhs.vdata[];
    return result;
  }

BOOM! adding (1) is enough to get the same error.

this is what is going on. i don't know why DMD insists on such restrictions for array operations, though.

Reply via email to