たとえば、LINQ ステートメントで新しいオブジェクトを作成する場合:
var list = new List<string>() { "a", "b", "c" };
var created = from i in list select new A();
クラスAは次のようになります。
class A
{
public string Label;
}
次に、 foreach ループを使用して A のプロパティを変更します。
foreach (var c in created) {
c.Label = "Set";
}
IEnumerable
後でオブジェクトにアクセスするときに値が設定されないのはなぜですか。たとえば、次のアサーションは失敗します。
Assert.AreEqual("Set", created.ElementAt(2).Label);
なぜこれが起こるのだろうか。foreach ステートメントがクエリを実行し、オブジェクトの作成をトリガーすることを期待します。MSDN のドキュメントには、「クエリ変数が foreach または For Each ループで繰り返されるまで、クエリの実行が延期される」と記載されています。
.NET 4.5 と Mono 3.2.0 でこの動作を再現しました。作成されたオブジェクトにアクセスする前にを呼び出すToList
と、この問題はなくなります。IEnumerable