On Thursday, 5 January 2023 at 23:05:17 UTC, thebluepandabear
wrote:
them or remove them.
I agree, forbidding function call syntax would be a great
usecase for `@property`.
It will probably never get implemented though.
In older versions, it worked when printing values with writeln.
But due to an error in formattedWrite, the program breaks. So I
stopped using @property. For example, you can't see the
difference in:
```d
struct Funy(T)
{
import std.conv : to;
this(X)(X x) {
value = x.to!T;
}
T value;
alias value this; // [a] getter
//@property
T opAssign(T x) { // [b] setter
return value = x;
}
alias opCall = opAssign; /* hack: `opAssign` methods
are not used for initialization,
but for subsequent assignments
[c] incrementor: */
//@property
T opOpAssign(string op: "+", X)(X x) {
return value = value + x.to!T;
}
}
import std.stdio;
void main()
{
auto funy = Funy!uint(20);
funy.value.writeln; // 20
funy = 10;
funy.value.writeln; // 1
class Fun
{
Funy!int n;
this(int i)
{
n = i; // or:
n(i + 1);
}
}
auto fun = new Fun(-2);
fun.n.writeln; // -1
fun.n += 19.999;
fun.n.writeln; // 18
}
```
Let's continue the fun...
```d
struct Funy(T)
{
this(T x) { value = x; }
T value;
alias opCall this;
//@property:
T opCall(T n) { return value = n; }
T opCall() { return value; }
}
import std.stdio;
void main()
{
auto funy = Funy!uint(20);
funy.value.writeln; // 20
funy = 10;
funy.value.writeln; // 1
class Fun
{
Funy!int n;
this(int i) {
n = i; // or:
n(i + 1);
}
}
auto fun = new Fun(-2);
fun.n.writeln; // -1
fun.n = 20;
fun.n.writeln; // 0
} /* PRINTS:
20
10
Funy!int(-1)
Funy!int(20)
```
If you don't want to get the above output you should use the
previous example. But don't forget to connect alias and opCall.
For example, you can use @property in version 2.0.83 without all
the fanfare.
SDB@79