Enumerable.GroupBy
andQueryable.GroupBy
扩展有 8 个重载。其中两个(对于Enumerable.GroupBy
)是:
// (a)
IEnumerable<TResult> GroupBy<TSource, TKey, TResult>(
this IEnumerable<TSource> source,
Func<TSource, TKey> keySelector,
Func<TKey, IEnumerable<TSource>, TResult> resultSelector);
// (b)
IEnumerable<TResult> GroupBy<TSource, TKey, TElement, TResult>(
this IEnumerable<TSource> source,
Func<TSource, TKey> keySelector,
Func<TSource, TElement> elementSelector,
Func<TKey, IEnumerable<TElement>, TResult> resultSelector);
(Queryable.GroupBy
同样,只是用Expression<Func<...
而不是Func<...
)
(b)
有一个额外elementSelector
的 as 参数。
在 MSDN 上是重载 (a)的示例和重载 (b) 的示例。它们都使用相同的示例源集合:
List<Pet> petsList = new List<Pet>
{
new Pet { Name="Barley", Age=8.3 },
new Pet { Name="Boots", Age=4.9 },
new Pet { Name="Whiskers", Age=1.5 },
new Pet { Name="Daisy", Age=4.3 }
};
示例 (a) 使用此查询:
var query = petsList.GroupBy(
pet => Math.Floor(pet.Age), // keySelector
(age, pets) => new // resultSelector
{
Key = age,
Count = pets.Count(),
Min = pets.Min(pet => pet.Age),
Max = pets.Max(pet => pet.Age)
});
示例 (b) 使用此查询:
var query = petsList.GroupBy(
pet => Math.Floor(pet.Age), // keySelector
pet => pet.Age, // elementSelector
(baseAge, ages) => new // resultSelector
{
Key = baseAge,
Count = ages.Count(),
Min = ages.Min(),
Max = ages.Max()
});
两个查询的结果完全相同。
问题 1:是否有任何我无法resultSelector
单独使用的查询以及我真正需要的地方elementSelector
?或者这两个重载的能力是否总是相同的,使用其中一种或另一种方式只是个人喜好问题?
问题 2:在使用 LINQ 查询语法时,这两种不同的重载是否存在对应关系?
(作为一个附带问题:当Queryable.GroupBy
与实体框架一起使用时,两个重载都会被翻译成完全相同的 SQL 吗?)