我正在阅读一本关于 C# 的高级书籍。而且,现在我正在阅读这一部分:
实现基于委托(delegate)的语法的 Linq 查询方法的幕后操作。
到目前为止,我已经阅读了Where
、Select
、Skip
、SkipWhile
、Take
, TakeWhile
方法。
而且,我知道 Defferred 和 Immediate 执行以及其中一些方法返回的 Iterator
。
Deferred execution is a pattern of the execution model by which the CLR ensures a value will be extracted only when it is required from the IEnumerable-based information source. When any Linq operator uses the deferred execution, the CLR encapsulates the related information, such as the original sequence, predicate, or selector (if any), into an iterator, which will be used when the information is extracted from the original sequence using ToListmethod or ForEachmethod or manually using the underlying GetEnumeratorand MoveNextmethods in C#.
现在让我们举这两个例子:
IList<int> series = new List<int>() { 1, 2, 3, 4, 5, 6, 7 };
// First example
series.Where(x => x > 0).TakeWhile(x => x > 0).ToList();
// Second example
series.Where(x => x > 0).Take(4).ToList();
当我设置断点并调试这两个语句时,我可以看到一个区别。
TakeWhile()
方法在项目满足 Where
语句中的条件时执行。但是,Take
方法不是这种情况。
第一条声明:
第二个声明:
你能解释一下为什么吗?
最佳答案
这不是完全清楚你的意思,但如果你问为什么你在 TakeWhile
中的 lambda 表达式中打断点,但你没有打断点在 Take
中,只是 Take
根本不接受委托(delegate)——它只接受一个数字。在查找要返回的值时没有要执行的用户定义代码,因此没有要命的断点。
在您使用 TakeWhile
的示例中,您有两个 lambda 表达式 - 一个用于 Where
,一个用于 TakeWhile
。因此,您可以进入那些 lambda 表达式的任一个。
重要的是要了解 Where
和 TakeWhile
方法本身仅被调用 一次 - 但它们返回的序列会评估传递给的委托(delegate)他们遇到的每个值。
你可能想看看我的 Edulinq blog series有关 LINQ 内部结构的更多详细信息。
关于c# - LINQ 方法执行序列,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24979144/