I thought I understood generics in C#, until I got something of a shock with the following simple code:
List<Tuple<int,string>> list = new List<Tuple<int,string>>();
list.Add( new Tuple<int,string>( 1, "abc" ) );
list.Add( new Tuple<int,string>( 2, "def" ) );
list.Add( new Tuple<int,string>( 3, "ghi" ) );
list[ 0 ].Item1 = 4;
Compiler Error: error CS0200: Property or indexer 'System.Tuple<int,string>.Item1' cannot be assigned to -- it is read only
I have to say, I don't understand why. In this case, I am assigning an integer, so it must have 4 bytes set aside for it somewhere in the heap, so why can't I assign to it? Even if I tried to assign the string, the tuple holds a reference to a string, both of which are allocated on the heap, so again why can't I re-assign it?
Puzzled, I thought I'd work around the problem using a struct of my own as follows:
private struct Foo
{
public Foo( int i, string s )
{
_position = i;
_name = s;
}
public int Position
{
get { return _position; }
set { _position = value; }
}
public string Name
{
get { return _name; }
set { _name = value; }
}
private int _position;
private string _name;
}
List<Foo> list = new List<Foo>();
list.Add( new Foo( 1, "abc" ) );
list.Add( new Foo( 2, "def" ) );
list.Add( new Foo( 3, "ghi" ) );
list[ 0 ].Position = 4;
Compiler error: error CS1612: Cannot modify the return value of 'System.Collections.Generic.List<Foo>.this[int]' because it is not a variable
This error message I
really didn't understand. I can probably think of workarounds for this, but I have to say that I'm not sure I understand what I am doing wrong.
Any help or pointers to good articles on this would be gratefully received.
Kind wishes ~ Patrick