在LINQ结果上将IEnumberable 转换为List ,导致巨大的性能损失

在LINQ结果上你喜欢这样:

var result = from x in Items select x; List list = result.ToList(); 

但是, ToList真的很慢,是否会使列表变得可变,因此转换速度很慢?

在大多数情况下,我可以设法让我的IEnumerableParalell.DistinctQuery但现在我想将项目绑定到DataGridView,因此我需要作为其他东西而不是IEnumerable ,关于如何获得ToList或任何性能的建议替换?

IEnumerable中的10个百万记录中, .ToList大约需要6秒钟。

.ToList()什么慢?

如果你在比较

 var result = from x in Items select x; List list = result.ToList(); 

 var result = from x in Items select x; 

你应该注意,由于查询被懒惰地评估,第一行根本没有做太多。 它不会检索任何记录。 延迟执行使得这种比较完全不公平

这是因为LINQ喜欢懒惰并尽可能少地工作。 这一行:

 var result = from x in Items select x; 

尽管您选择了名称,但实际上并不是结果,它只是一个查询对象。 它不会获取任何数据。

 List list = result.ToList(); 

现在你实际上已经请求了结果,因此它必须从源获取数据并复制它。 ToList保证复制。

考虑到这一点,第二行比第一行慢得多并不奇怪。

不,它不会创建需要时间的列表,它正在获取需要时间的数据。

您的第一个代码行实际上并不获取数据,它只设置一个能够获取数据的IEnumerable。 当你调用ToList方法它实际上将获得所有数据时,这就是所有执行时间都在第二行的原因。

您还应该考虑在网格中有一千万行是否有用。 没有用户会查看所有行,因此实际上并没有任何意义。 也许你应该提供一种在获取任何数据之前过滤结果的方法。

我认为这是因为内存重新分配: ToList事先无法知道集合的大小,因此它可以分配足够的存储空间来保存所有项目。 因此,它必须在List增长时重新分配。

如果您可以估计结果集的大小,使用List(int)构造函数重载预分配足够的元素,然后手动向其添加项目会快得多。