Expanding on your comment a bit, in c# when you declare a new type, you decide whether it is a reference type(class), or a value type(struct). These declarations govern usage semantics.
Classes: are passed by reference. .Equals and == will compare references for equality(unless overriden).
Structs: are passed by value. .Equals and == will do a memberwire comparison to test for equality.
However, you can pass both structs and classes by reference, using the ref keyword. This does the obvious thing for a struct (For a class, it passes the pointer by reference). However, you are limited to passing method arguments by reference - you cannot pass return types by reference. So it is impossible to make a getter return a value by reference, which is what you are looking for.
Now, let us consider the ramifications of allowing pass-by-reference of value types. C++ lets you do something that is quite evil:
int& foo(){ int local = 5; return local;}
When foo exits, a reference to local is still around - even though the stack for local has been cleaned up! Let's try a different tack: allowing the programmer to declare a value type to be instantiated as a reference type.
ref int foo(){ ref int local = 5; return local;}
There are some things that fall out of such a solution. One, you would have to allow conversions between ref-declared value types and non-ref-declared value types. This is murky, because you would like to preserve references whenever possible, as in the following example:
class Point{ private float x, y; public ref float X { get { return this.x; } } public ref float Y { get { return this.y; } }}
We surely don't want to have to declare x and y as ref in our class(since they would be allocated external to the Point class). So we have to allow a conversion from a value-type field to a ref-value type. But what if Point is declared as a struct? Now, the previously mentioned conversion is illegal, since x and y would be declared on the stack and could fall out of scope. You could enforce a pointer check on any ref-value type before derefing it, but how can you ensure that it is still valid?
Notice the huge number of special cases and exceptions given the proposed feature. Also, consider that, for the most part, you will treat reference types as reference types, and value types as value types. So should C# make the type declaration rules more complex to support a small set of cases? The language designers said no, and I think they made the right choice.
Also, read what the .NET design guidelines have to say.Quote:
DO NOT define a struct unless the type has all of the following characteristics:
It logically represents a single value, similar to primitive types (int, double, etc.).
It has an instance size under 16 bytes.
It is immutable.
It will not have to be boxed frequently.
In all other cases, you should define your types as classes.
The problems you are having with value types go away when using immutable value types. Now, it's probably the right decision to make your point/vector class a struct, but now you know why it's such a pain to change them when they are exposed as properties.
Finally, consider the following code:
List<Point> myPoints; ...// set a pointmyPoints[0] = new Point(25, 0);// add something to a pointmyPoints[1] += new Vector(10, 0);
Was that so hard? ;)