这是从 SingleOrDefault 函数中提取的代码:
public static TSource SingleOrDefault<TSource>(this IEnumerable<TSource> source, Func<TSource, bool> predicate) {
if (source == null) throw Error.ArgumentNull("source");
if (predicate == null) throw Error.ArgumentNull("predicate");
TSource result = default(TSource);
long count = 0;
foreach (TSource element in source) {
if (predicate(element)) {
result = element;
checked { count++; }
}
}
switch (count) {
case 0: return default(TSource);
case 1: return result;
}
throw Error.MoreThanOneMatch();
}
我想知道是否有任何原因在循环中找到多个元素后,没有 break 语句来防止循环列表的其余部分。无论如何,都会发生错误。对于在开头找到多个项目的大列表,我认为这会产生很大的不同。
最佳答案
乔恩双向飞碟 found this while reimplementing LINQ to objects as part of his EduLinq blog series :
It turns out that in LINQ to Objects, the overloads without a predicate throw InvalidOperationException as soon as they see a second element, but the overloads with a predicate keep iterating even when they've seen a second element matching a predicate. This seems ludicrously inconsistent to me - I've opened a Connect issue about it; we'll see what happens.
在Connect issue in question , 微软说:
This would be great to clean up, so that iterating the entire sequence is not required when using the
Single
overload that takes a predicate - we could fail fast upon finding a second match, similar to what we do when no predicate is specified.However, as the perf benefit to be had here would be limited to
Single
's error case, this issue currently falls just below our bug triage cut line. We're marking the issue Won't Fix to indicate that we're not currently tracking to fix this issue in the next release of Visual Studio. We'll reactivate this bug over the next year if we get further than expected through our bug triage list, or if we revisit the bug for the following release.
那是在 2011 年 4 月......
关于c# - Linq的SingleOrDefault函数中的优化,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/14940434/