Why can't we define re-assignable const reference variable?
Steven Schveighoffer
schveiguy at yahoo.com
Tue Feb 19 13:34:39 PST 2008
"Walter Bright" wrote
> Sergey Gromov wrote:
>> I'm talking from the standpoint of generalization which you so much care
>> about. When I generalize, I don't care how things are implemented. It's
>> behaviour that matters. If I create an algorithm that uses references to
>> invariant data, then it will work with anything that /behaves/ like such
>> references. Even if they are actually ints passed by value.
>
> That's a good point, and a good reason why:
>
> invariant(C)[] c;
> invariant(int)[] i;
>
> should both have immutable array contents, i.e. if the contents of a
> reference is invariant then the reference itself should be invariant.
>
> The concept of having a mutable reference to immutable data is
> fundamentally flawed because it breaks the concept of what a reference is.
> A reference is not separable from what it refers to. If they were
> separable, they would be syntactically and semantically the same thing as
> pointers, and there would be no point whatsoever to even having a
> reference type.
So please explain this:
import std.stdio;
class C
{
this(int n) {x = n;}
int x;
}
void assignit(ref int src, ref int value)
{
src = value;
}
void assignit(C src, C value)
{
src = value;
}
void main()
{
int n = 1;
int m = 2;
C c = new C(1);
C d = new C(2);
assignit(n, m);
assignit(c, d);
writefln("%s %s %s %s", n, m, c.x, d.x);
}
// outputs 2 2 1 2
In both cases, the assignit function is taking reference types as arguments.
C is a reference type because it is a class. ref int is a reference type
because the compiler magically creates a reference. Both do the same thing,
but yet the class version doesn't result in the value changing, because we
are rebinding the reference, not copying the class itself. This is why your
argument fails. There are some cases in D where references are treated as
non-rebindable pointers to data, where acting on the reference is equivalent
to acting on the pointed at data, and then there are classes, where you can
rebind the reference in some cases, but in other cases you are acting on the
data pointed to.
I'm not saying that references should always be non-rebindable (I like the
way classes work) or always be rebindable, I'm just saying that your
argument against allowing references to be acted upon separate from the data
is against the way the language/compiler currently is implemented.
You can make the case that class references are not the same as
non-rebindable references, and also that they are not like pointers. I
would say that they are exactly like pointers except you cannot dereference
them or perform general arithmetic on them. This puts them in a category on
their own, which I think is fair game to say that it is reasonable that we
can ask for that category to be modified without affecting the consistency
of the other categories.
The specific modification being that you can const-ify the data pointed to
by a class reference without modifying the reference constness itself.
-Steve
More information about the Digitalmars-d
mailing list