Enumerable.Range
不可重复;它将重新执行所有操作(创建新对象等)
每次迭代
。我们可以测试一下:
var seq = Enumerable.Range(1241241, 1).Select(i => i.ToString());
var a = seq.Single();
var b = seq.Single();
Console.WriteLine($"{a == b}, {ReferenceEquals(a, b)}");
哪个输出
True, False
因为不同
实例
已为两次迭代创建了字符串(通过
Single()
).
更一般地说:
任何
IEnumerable<T>
可能或可能不会
可重复。列表、数组等:通常是可重复的(只要不更改数据)。更复杂的序列——例如,从套接字、外部数据源或RNG读取:没那么多。
添加
.ToList()
意味着原始序列只迭代一次,并缓冲到一个列表中,然后
是
可重复。添加
.ToList()
上面测试的第一行给了我们
True, True
.
注:
.Select
本身就是
也
不可重复;如果你有一个列表,然后通过创建一个序列
list.Select(...)
:该序列将
也
每次迭代时,都要重新执行所有的投影逻辑。对于大多数LINQ操作,情况也是如此。