Csharp/C#教程:C#foreach on IEnumerable vs. List – 元素修改仅对数组持久 – 为什么?分享


C#foreach on IEnumerable vs. List – 元素修改仅对数组持久 – 为什么?

在C#中,我注意到如果我在LINQ生成的IEnumerable集合上运行foreach循环并尝试修改每个T元素的内容,那么我的修改不会持久。

另一方面,如果在创建集合时应用ToArray()ToList()方法,则对foreach循环各个元素的修改持久的。

我怀疑这在某种程度上与延迟执行有关,但究竟对我来说并不完全是显而易见的。 我真的很感激这种行为差异的解释。

这是一些示例代码 – 我有一个带有构造函数和自动实现属性的类MyClass

 public class MyClass { public MyClass(int val) { Str = val.ToString(); } public string Str { get; set; } } 

在我的示例应用程序中,我使用LINQ Select()通过最终应用ToList()方法,基于整数集合创建两个MyClass对象集合,一个IEnumerable和一个IList

 var ints = Enumerable.Range(1, 10); var myClassEnumerable = ints.Select(i => new MyClass(i)); var myClassArray = ints.Select(i => new MyClass(i)).ToList(); 

接下来,我在每个集合上运行一个foreach循环,并修改循环的MyClass对象的内容:

 foreach (var obj in myClassEnumerable) obj.Str = "Something"; foreach (var obj in myClassArray) obj.Str = "Something else"; 

最后,我输出每个集合中第一个元素的Str成员:

 Console.WriteLine(myClassEnumerable.First().Str); Console.WriteLine(myClassArray.First().Str); 

有点违反直觉,输出是:

 1 Something else 

延期执行确实是关键点。

执行myClassEnumerable.First().Str将重新执行你的查询ints.Select(i => new MyClass(i)); 所以它会给你一个新的IEnumerable和一个新的整数列表。

您可以使用调试器查看此操作。 在IEnumerable select的new MyClass(i)部分放置一个断点,当你为Console.WriteLine执行它时,你会看到这个部分再次被击中

你是对的,它是延期执行。 每次迭代IEnumerable时都会创建一个新的MyClass实例。 通过调用ToList或ToArray,然后创建一个List或Array,并使用从IEnumerable的迭代创建的新MyClass实例填充它。

上述就是C#学习教程:C#foreach on IEnumerable vs. List – 元素修改仅对数组持久 – 为什么?分享的全部内容,如果对大家有所用处且需要了解更多关于C#学习教程,希望大家多多关注—计算机技术网(www.ctvol.com)!

本文来自网络收集,不代表计算机技术网立场,如涉及侵权请联系管理员删除。

ctvol管理联系方式QQ:251552304

本文章地址:https://www.ctvol.com/cdevelopment/987259.html

(0)
上一篇 2021年12月22日
下一篇 2021年12月22日

精彩推荐