On Thursday, 21 November 2013 at 06:48:40 UTC, qznc wrote:
On Wednesday, 20 November 2013 at 22:49:42 UTC, Spott wrote:
I've been screwing around with templates lately, and I'm
attempting to figure out why the following won't compile:

struct value
{
    int a;

    const auto
        opBinary(string op, T)(in T rhs) const pure {
            static if (op == "+")
return intermediateValue!(value.plus,this,rhs)();
        }

    ref value opAssign(T)( in T t ) {
        a = t.a;
        return this;
    }

    static
    int plus(T1, T2)(in T1 x, in T2 y) pure {
        return x.a + y.a;
    }

}

struct intermediateValue(alias Op, alias A, alias B)
{

    auto opBinary(string op, T)(in T rhs) const pure {
        static if (op == "+")
            return intermediateValue!(value.plus,this,rhs)();
    }

    @property auto a() const pure {
        return Op(A, B);
    }

}

void main()
{
    value a = value(2);
    value b = value(3);
    value c;
    c = a + b;
}

The error is:
d_playground.d(34): Error: pure nested function 'a' cannot access
mutable data 'this'
d_playground.d(34): Error: pure nested function 'a' cannot access
mutable data 'this'
d_playground.d(10): Error: template instance
d_playground.value.opBinary!("+",
value).opBinary.intermediateValue!(plus, this, rhs) error
instantiating
d_playground.d(44): instantiated from here: opBinary!("+",
value)
d_playground.d(44): Error: template instance
d_playground.value.opBinary!("+", value) error instantiating

What is going on?  Why is 'a' not allowed to "access" mutable
data (even though it isn't modifying it)? How do I tell the
compiler to pass "this" in a const fashion?

No answer, but two notes.

First, use dpaste for such code snippets: http://dpaste.dzfl.pl/f2f39b32

Second, what are you trying to do? intermediateValue is a struct without members. I am not sure what 'this' means in such a case.

intermediateValue is a structure that ideally should only exist
at compile time.

Theoretically, (at least in my head), opAssign will traverse the
expression and reduce it to the addition that it is inside
opAssign.

I'm attempting to create a vector DSL (similar to blaze-lib:
https://code.google.com/p/blaze-lib/), but starting with just a
plain number.  Mostly it is for fun, it is a way of working on my
understanding of the compile time primitives and template system.

Reply via email to