I have a scope question regarding Linq expressions that are defined in a loop. The following LinqPad C# Program demonstrates the behaviour:
void Main()
{
string[] data=new string[] {"A1", "B1", "A2", "B2" };
string[] keys=new string[] {"A", "B" };
List<Result> results=new List<Result>();
foreach (string key in keys) {
IEnumerable<string> myData=data.Where (x => x.StartsWith(key));
results.Add(new Result() { Key=key, Data=myData});
}
results.Dump();
}
// Define other methods and classes here
class Result {
public string Key { get; set; }
public IEnumerable<string> Data { get; set; }
}
Basically, "A" should have data [A1, A2] and "B" should have data [B1, B2].
However, when you run this "A" gets data [B1, B2] as does B. I.e. the last expression is evaluated for all instances of Result.
Given that I declared "myData" inside the loop, why is it behaving as if I declared it outside the loop? EG it is acting like I would expect if I did this:
void Main()
{
string[] data=new string[] {"A1", "B1", "A2", "B2" };
string[] keys=new string[] {"A", "B" };
List<Result> results=new List<Result>();
IEnumerable<string> myData;
foreach (string key in keys) {
myData=data.Where (x => x.StartsWith(key));
results.Add(new Result() { Key=key, Data=myData});
}
results.Dump();
}
// Define other methods and classes here
class Result {
public string Key { get; set; }
public IEnumerable<string> Data { get; set; }
}
I get the desired result if I force the evaluation inside the iteration, that is not my question.
I'm asking why "myData" is seemingly shared across iterations given that I declared it within scope of a single iteration?
Somebody call Jon Skeet... ;^)