尝试使用await
关键字在LINQ
查询,我得到这个:
该“等待”操作可以仅在查询表达式“从”子句或“加入”子句的集合表达中使用的初始的第一集合表达内
示例代码:
var data = (from id in ids
let d = await LoadDataAsync(id)
select d);
它是不可能等待在一些LINQ
查询,或是否需要进行结构不同的方式?
尝试使用await
关键字在LINQ
查询,我得到这个:
该“等待”操作可以仅在查询表达式“从”子句或“加入”子句的集合表达中使用的初始的第一集合表达内
示例代码:
var data = (from id in ids
let d = await LoadDataAsync(id)
select d);
它是不可能等待在一些LINQ
查询,或是否需要进行结构不同的方式?
LINQ有非常有限的支持async
/ await
。 对于LINQ到对象,我所知道的唯一的真正有用的工作是做一个Select
与async
委托(这将导致任务序列)。
List<T> data = new List<T>();
foreach (var id in ids)
data.Add(await LoadDataAsync(id));
如果你能做到LoadDataAsync
并行的方式安全,您的例子可以写成:
T[] data = await Task.WhenAll(ids.Select(id => LoadDataAsync(id)));
你可以自己定义一些异步LINQ操作(LINQ对象):例如:你可以写你自己的WhereAsync扩展方法:
public static async Task<IEnumerable<T>> WhereAsync<T>(
this IEnumerable<T> target, Func<T, Task<bool>> predicateAsync)
{
var tasks = target.Select(async x => new { Predicate = await predicateAsync(x).ConfigureAwait(false), Value = x }).ToArray();
var results = await Task.WhenAll(tasks).ConfigureAwait(false);
return results.Where(x => x.Predicate).Select(x => x.Value);
}
并使用它像:
var ints = new List<int> { 1, 2, 3 };
var smallInts = await ints.WhereAsync(IsSmallIntAsync);
使用无功扩展,它可以异步处理LINQ查询的结果是这样的:
(from d in ids
select LoadDataAsync(d).ToObservable()).Merge()
这是给你,你可以以各种方式应对可观察到的数据流。 例如,您可以.Buffer结果与超时列表。
在本质上是以上说“在IDS每d,应用异步函数到它,这将产生用于每个d一项任务,并治疗如可观察到的单个结果(ToObservable),并治疗所有那些可观察在一起作为单个可观察到的流(合并)