Enumerable.SelectMany 方法
定义
- 命名空间:
- System.Linq
- 程序集:
- System.Linq.dll
将序列的每个元素投影到 IEnumerable<T> 并将结果序列合并为一个序列。
重载
SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>) |
将序列的每个元素投影到 IEnumerable<T>,并将结果序列合并为一个序列,并对其中每个元素调用结果选择器函数。 |
SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>) |
将序列的每个元素投影到 IEnumerable<T>,并将结果序列合并为一个序列,并对其中每个元素调用结果选择器函数。 每个源元素的索引用于该元素的中间投影表。 |
SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TResult>>) |
将序列的每个元素投影到 IEnumerable<T> 并将结果序列合并为一个序列。 |
SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TResult>>) |
将序列的每个元素投影到 IEnumerable<T> 并将结果序列合并为一个序列。 每个源元素的索引用于该元素的投影表。 |
SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)
将序列的每个元素投影到 IEnumerable<T>,并将结果序列合并为一个序列,并对其中每个元素调用结果选择器函数。
C#public static System.Collections.Generic.IEnumerable<TResult> SelectMany<TSource,TCollection,TResult> (this System.Collections.Generic.IEnumerable<TSource> source, Func<TSource,System.Collections.Generic.IEnumerable<TCollection>> collectionSelector, Func<TSource,TCollection,TResult> resultSelector);
类型参数
- TSource
source
的元素类型。
- TCollection
collectionSelector
收集的中间元素的类型。
- TResult
结果序列的元素的类型。
参数
- source
- IEnumerable<TSource>
一个要投影的值序列。
- collectionSelector
- Func<TSource,IEnumerable<TCollection>>
应用于输入序列的每个元素的转换函数。
- resultSelector
- Func<TSource,TCollection,TResult>
应用于中间序列的每个元素的转换函数。
返回
IEnumerable<TResult>一个 IEnumerable<T>,其元素是通过以下方法得到的:对 source
的每个元素调用一对多转换函数 collectionSelector
,然后将这些序列元素中的每一个元素及其相应的源元素映射到一个结果元素。
例外
ArgumentNullExceptionsource
、collectionSelector
或 resultSelector
为 null
。
示例
下面的代码示例演示如何使用 SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>) 对数组执行一对多投影,并使用结果选择器函数将源序列中的每个对应元素保留在对 的最后调用 Select
的范围内。
class PetOwner
{
public string Name { get; set; }
public List<string> Pets { get; set; }
}
public static void SelectManyEx3()
{
PetOwner[] petOwners =
{ new PetOwner { Name="Higa",
Pets = new List<string>{ "Scruffy", "Sam" } },
new PetOwner { Name="Ashkenazi",
Pets = new List<string>{ "Walker", "Sugar" } },
new PetOwner { Name="Price",
Pets = new List<string>{ "Scratches", "Diesel" } },
new PetOwner { Name="Hines",
Pets = new List<string>{ "Dusty" } } };
// Project the pet owner's name and the pet's name.
var query =
petOwners
.SelectMany(petOwner => petOwner.Pets, (petOwner, petName) => new { petOwner, petName })
.Where(ownerAndPet => ownerAndPet.petName.StartsWith("S"))
.Select(ownerAndPet =>
new
{
Owner = ownerAndPet.petOwner.Name,
Pet = ownerAndPet.petName
}
);
// Print the results.
foreach (var obj in query)
{
Console.WriteLine(obj);
}
}
// This code produces the following output:
//
// {Owner=Higa, Pet=Scruffy}
// {Owner=Higa, Pet=Sam}
// {Owner=Ashkenazi, Pet=Sugar}
// {Owner=Price, Pet=Scratches}
注解
此方法通过使用延迟执行来实现。 即时返回值是一个对象,用于存储执行操作所需的所有信息。 在通过直接调用GetEnumerator
其方法或在 C# For Each
或 foreach
Visual Basic 中使用 来枚举对象之前,不会执行此方法表示的查询。
SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)当必须将 的source
元素保留在调用 SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)后发生的查询逻辑的范围内时,方法非常有用。 有关代码示例,请参见“示例”部分。 如果 类型的对象与 类型的 TSource
对象之间存在双向关系,即,如果 类型的TCollection
对象提供属性来检索TSource
生成它的 对象,则不需要 的此重载SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)TCollection
。 相反,可以使用 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TResult>>) 并通过 对象TCollection
导航回 TSource
对象。
在查询表达式语法中,在初始子句转换为 调用 SelectMany后,每个from
子句 (C#) 或 From
子句 (Visual Basic) 。
另请参阅
适用于
.NET 9 和其他版本SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)
将序列的每个元素投影到 IEnumerable<T>,并将结果序列合并为一个序列,并对其中每个元素调用结果选择器函数。 每个源元素的索引用于该元素的中间投影表。
C#public static System.Collections.Generic.IEnumerable<TResult> SelectMany<TSource,TCollection,TResult> (this System.Collections.Generic.IEnumerable<TSource> source, Func<TSource,int,System.Collections.Generic.IEnumerable<TCollection>> collectionSelector, Func<TSource,TCollection,TResult> resultSelector);
类型参数
- TSource
source
的元素类型。
- TCollection
collectionSelector
收集的中间元素的类型。
- TResult
结果序列的元素的类型。
参数
- source
- IEnumerable<TSource>
一个要投影的值序列。
- collectionSelector
- Func<TSource,Int32,IEnumerable<TCollection>>
一个应用于每个源元素的转换函数;函数的第二个参数表示源元素的索引。
- resultSelector
- Func<TSource,TCollection,TResult>
应用于中间序列的每个元素的转换函数。
返回
IEnumerable<TResult>一个 IEnumerable<T>,其元素是通过以下方法得到的:对 source
的每个元素调用一对多转换函数 collectionSelector
,然后将这些序列元素中的每一个元素及其相应的源元素映射到一个结果元素。
例外
ArgumentNullExceptionsource
、collectionSelector
或 resultSelector
为 null
。
注解
此方法通过使用延迟执行来实现。 即时返回值是一个对象,用于存储执行操作所需的所有信息。 在通过直接调用GetEnumerator
其方法或在 C# For Each
或 foreach
Visual Basic 中使用 来枚举对象之前,不会执行此方法表示的查询。
SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)当必须将 的source
元素保留在调用 SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)后发生的查询逻辑的范围内时,方法非常有用。 有关代码示例,请参见“示例”部分。 如果 类型的对象与 类型的 TSource
对象之间存在双向关系,即,如果 类型的TCollection
对象提供属性来检索TSource
生成它的 对象,则不需要 的此重载SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)TCollection
。 相反,可以使用 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TResult>>) 并通过 对象TCollection
导航回 TSource
对象。
适用于
.NET 9 和其他版本SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TResult>>)
将序列的每个元素投影到 IEnumerable<T> 并将结果序列合并为一个序列。
C#public static System.Collections.Generic.IEnumerable<TResult> SelectMany<TSource,TResult> (this System.Collections.Generic.IEnumerable<TSource> source, Func<TSource,System.Collections.Generic.IEnumerable<TResult>> selector);
类型参数
- TSource
source
的元素类型。
- TResult
selector
返回的序列元素的类型。
参数
- source
- IEnumerable<TSource>
一个要投影的值序列。
- selector
- Func<TSource,IEnumerable<TResult>>
应用于每个元素的转换函数。
返回
IEnumerable<TResult>一个 IEnumerable<T>,其元素是对输入序列的每个元素调用一对多转换函数得到的结果。
例外
ArgumentNullExceptionsource
或 selector
为 null
。
示例
下面的代码示例演示如何使用 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TResult>>) 对数组执行一对多投影。
C#class PetOwner
{
public string Name { get; set; }
public List<String> Pets { get; set; }
}
public static void SelectManyEx1()
{
PetOwner[] petOwners =
{ new PetOwner { Name="Higa, Sidney",
Pets = new List<string>{ "Scruffy", "Sam" } },
new PetOwner { Name="Ashkenazi, Ronen",
Pets = new List<string>{ "Walker", "Sugar" } },
new PetOwner { Name="Price, Vernette",
Pets = new List<string>{ "Scratches", "Diesel" } } };
// Query using SelectMany().
IEnumerable<string> query1 = petOwners.SelectMany(petOwner => petOwner.Pets);
Console.WriteLine("Using SelectMany():");
// Only one foreach loop is required to iterate
// through the results since it is a
// one-dimensional collection.
foreach (string pet in query1)
{
Console.WriteLine(pet);
}
// This code shows how to use Select()
// instead of SelectMany().
IEnumerable<List<String>> query2 =
petOwners.Select(petOwner => petOwner.Pets);
Console.WriteLine("\nUsing Select():");
// Notice that two foreach loops are required to
// iterate through the results
// because the query returns a collection of arrays.
foreach (List<String> petList in query2)
{
foreach (string pet in petList)
{
Console.WriteLine(pet);
}
Console.WriteLine();
}
}
/*
This code produces the following output:
Using SelectMany():
Scruffy
Sam
Walker
Sugar
Scratches
Diesel
Using Select():
Scruffy
Sam
Walker
Sugar
Scratches
Diesel
*/
注解
此方法通过使用延迟执行来实现。 即时返回值是一个对象,用于存储执行操作所需的所有信息。 在通过直接调用GetEnumerator
其方法或在 C# For Each
或 foreach
Visual Basic 中使用 来枚举对象之前,不会执行此方法表示的查询。
方法 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TResult>>) 枚举输入序列,使用转换函数将每个元素映射到 , IEnumerable<T>然后枚举并生成每个此类 IEnumerable<T> 对象的元素。 也就是说,对于 的每个元素 source
, selector
将调用 并返回一系列值。 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TResult>>) 然后,将此集合的二维集合平展为一维 IEnumerable<T> 并返回它。 例如,如果查询使用 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TResult>>) 获取数据库中每个客户) 类型的 Order
订单 (,则结果的类型为 IEnumerable<Order>
C# 或 IEnumerable(Of Order)
Visual Basic。 如果查询改为使用 Select 来获取订单,则不会组合订单集合集合,并且结果的类型为 IEnumerable<List<Order>>
C# 或 IEnumerable(Of List(Of Order))
Visual Basic。
在查询表达式语法中,在初始子句转换为 调用 SelectMany后,每个from
子句 (C#) 或 From
子句 (Visual Basic) 。
另请参阅
适用于
.NET 9 和其他版本SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TResult>>)
将序列的每个元素投影到 IEnumerable<T> 并将结果序列合并为一个序列。 每个源元素的索引用于该元素的投影表。
C#public static System.Collections.Generic.IEnumerable<TResult> SelectMany<TSource,TResult> (this System.Collections.Generic.IEnumerable<TSource> source, Func<TSource,int,System.Collections.Generic.IEnumerable<TResult>> selector);
类型参数
- TSource
source
的元素类型。
- TResult
selector
返回的序列元素的类型。
参数
- source
- IEnumerable<TSource>
一个要投影的值序列。
- selector
- Func<TSource,Int32,IEnumerable<TResult>>
一个应用于每个源元素的转换函数;函数的第二个参数表示源元素的索引。
返回
IEnumerable<TResult>一个 IEnumerable<T>,其元素是对输入序列的每个元素调用一对多转换函数得到的结果。
例外
ArgumentNullExceptionsource
或 selector
为 null
。
示例
下面的代码示例演示如何使用 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TResult>>) 对数组执行一对多投影,并使用每个外部元素的索引。
C#class PetOwner
{
public string Name { get; set; }
public List<string> Pets { get; set; }
}
public static void SelectManyEx2()
{
PetOwner[] petOwners =
{ new PetOwner { Name="Higa, Sidney",
Pets = new List<string>{ "Scruffy", "Sam" } },
new PetOwner { Name="Ashkenazi, Ronen",
Pets = new List<string>{ "Walker", "Sugar" } },
new PetOwner { Name="Price, Vernette",
Pets = new List<string>{ "Scratches", "Diesel" } },
new PetOwner { Name="Hines, Patrick",
Pets = new List<string>{ "Dusty" } } };
// Project the items in the array by appending the index
// of each PetOwner to each pet's name in that petOwner's
// array of pets.
IEnumerable<string> query =
petOwners.SelectMany((petOwner, index) =>
petOwner.Pets.Select(pet => index + pet));
foreach (string pet in query)
{
Console.WriteLine(pet);
}
}
// This code produces the following output:
//
// 0Scruffy
// 0Sam
// 1Walker
// 1Sugar
// 2Scratches
// 2Diesel
// 3Dusty
注解
此方法通过使用延迟执行来实现。 即时返回值是一个对象,用于存储执行操作所需的所有信息。 在通过直接调用GetEnumerator
其方法或在 C# For Each
或 foreach
Visual Basic 中使用 来枚举对象之前,不会执行此方法表示的查询。
方法 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TResult>>) 枚举输入序列,使用转换函数将每个元素映射到 , IEnumerable<T>然后枚举并生成每个此类 IEnumerable<T> 对象的元素。 也就是说,对于 的每个元素 source
, selector
将调用 并返回一系列值。 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TResult>>) 然后,将此集合的二维集合平展为一维 IEnumerable<T> 并返回它。 例如,如果查询使用 SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TResult>>) 获取数据库中每个客户) 类型的 Order
订单 (,则结果的类型为 IEnumerable<Order>
C# 或 IEnumerable(Of Order)
Visual Basic。 如果查询改为使用 Select 来获取订单,则不会组合订单集合集合,并且结果的类型为 IEnumerable<List<Order>>
C# 或 IEnumerable(Of List(Of Order))
Visual Basic。
第一个参数表示 selector
要处理的元素。 第二个参数表示 selector
源序列中该元素的从零开始的索引。 例如,如果元素采用已知顺序并且你想要对特定索引处的元素执行某些操作,则这非常有用。 如果要检索一个或多个元素的索引,它也很有用。
适用于
.NET 9 和其他版本.NET 反馈
.NET 是一个开放源代码项目。 选择一个链接以提供反馈:
提出文档问题 提供产品反馈本文内容
- 定义
- 重载
- SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)
- SelectMany<TSource,TCollection,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TCollection>>, Func<TSource,TCollection,TResult>)
- SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,IEnumerable<TResult>>)
- SelectMany<TSource,TResult>(IEnumerable<TSource>, Func<TSource,Int32,IEnumerable<TResult>>)