On Saturday, 4 August 2012 at 19:08:58 UTC, Jacob Carlborg wrote:
I don't think that's correct behavior. I think the correct
behavior would be to have a property rewrite, something like
this:
Yes, I agree in general, but if a getter returns a ref, you should
be able to write to it... I think anyway, but it is an lvalue
anyway.
What I just added to my hacked compiler is this:
=====
else if(e1->op == TOKcall) {
// for property work, if there is a setter, we should
revert to the older style
// handling. If not, we can keep it as a CallExp
CallExp* ce = (CallExp*) e1;
Expression* temp_e1 = ce->e1;
if((temp_e1->op == TOKvar &&
temp_e1->type->toBasetype()->ty == Tfunction)) {
// this is potentially a setter.... but not
necessarily
fd = ((VarExp
*)temp_e1)->var->isFuncDeclaration();
ethis = NULL;
assert(fd);
FuncDeclaration *f = fd;
Expressions a;
a.push(e2);
fd = f->overloadResolve(loc, ethis, &a, 1);
if (fd && fd->type) {
e1 = temp_e1;
goto Lsetter;
}
}
=====
To line 10320 - right above where the old style setter code is.
It isn't perfect yet because it doesn't ensure we are dealing
with a @property, but it is closer.
The idea is: if we have a setter function, we should try to use
it, just like dmd does today. If not, we'll leave the call there
and see what happens. (If it returns ref, it will work,
otherwise, it errors saying the property is not an lvalue.)
So far this is passing my simple test for assignment, but not yet
the op assigns.
int a;
@property int funcprop() {
return a;
}
// setter
@property int funcprop(int s) {
return a = s + 10;
}
funcprop = 10; // works, funcprop == 20 now
funcprop += 10; // currently does NOT work
Is rewritten as:
auto __tmp = foo;
foo = __tmp + 10;
I think this is exactly what we have to do to work in all cases.
I'm gonna take a look at it next... then it is time to test this
patch and with a little luck, we can finally put the property
debate to rest.
I think that you should always be able to replace a variable
with a property. The other way around I'm not so sure. The
problem is with methods in classes. Since a method will be
virtual by default you can't just replace a property with a
variable. That could potentially break subclasses that override
the property.
True. I think all the other uses should just work though.