I'm using a Dictionary<int, KeyValuePair<bool, int>>
to hold data.
From time to time I need to increment the int
in the KeyValuePair
, but it won't let me, because it has no setter. Is there a way to increment it?
Code sample:
Dictionary<int, KeyValuePair<bool, int>> mDictionary =
new Dictionary<int, KeyValuePair<bool, int>>();
mDictionary[trapType].Value++;
//Error: The property KeyValuePair<TKey, Tvalue>>.Value has no setter
No.
KeyValuePair
is immutable - it's also a value type, so changing the value of theValue
property after creating a copy wouldn't help anyway.You'd have to write something like this:
It's pretty ugly though - do you really need the value to be a
KeyValuePair
?another solution is to create a new dictionary and pass the new values and keys to it:
Conceptually,
KeyValuePair<TKey,TValue>
is just a pair of variables,Key
andValue
. Had Microsoft implemented it with exposed public fieldsKey
andValue
, the semantics of it would have been perfect; when used as aForEach
control variable it would have been immutable, but one could have updated the Key or Value field of an ordinary variable or array element without having to update the other.Unfortunately, Microsoft seems to have been unwilling to have framework types expose any public fields, even for types like
KeyValuePair<TKey,TValue>
orDrawing.Rectangle
whose semantics dictate that (1) the type must be a struct; (2) its entire state is visible in a fixed set of properties (there may be other computed properties beyond those which define an object's state), and (3) those properties may be assigned any combination of values suitable for their types. Consequently, Microsoft only considered the possibilities of exposing the members comprising the types' state as read-only properties, or as read-write properties. Using read-write properties would mean that code like:or
would be interpreted by the existing C# compiler as either
or
both of yield horrible behavior which is almost certainly not what the programmer intended. The implementers of .net decided that the value of having the members of
KeyValuePair<TKey,TValue>
be individually mutable did not justify the danger posed by the former, but the usefulness of modifying individual members ofRectangle
was sufficient to justify the danger posed by second. Note that neither example would have had to pose any danger had the types used exposed fields rather than properties, since writing to a field of a temporary struct has never been permissible, even when calling property setters was.KeyValuePair
tends just to be used as an iterator value for dictionaries. You're better off defining your own type if you want it to be mutable.As previously mentioned, the KeyValuePair is immutable. I thought it was worth adding here a mutable implementation: