The technical reason is that mutable structs appear to be able to do things that they don't actually do. Since the design-time semantics are the same as reference types, this becomes confusing for developers. This code:
public void DoSomething(MySomething something)
{
something.Property = 10;
}
Behaves quite differently depending on if MySomething
is a struct
or a class
. To me, this is a compelling, but not the most compelling reason. If you look at DDD's Value Object, you can see the connection to how structs should be treated. A value object in DDD can be best represented as a value type in .Net (and therefore a struct). Because it has no identity, it can't change.
Think of this in terms of something like your address. You can "change" your address, but the address itself hasn't changed. In fact, you have a new address assigned to you. Conceptually, this works, because if you actually changed your address, your roommates would have to move too.