说我想让第42组的每个人都在这里,但是我想获取数据库中每个唯一名字的IQueryable(PS-我知道我可以在Select之后调用AsQueryable(),但这不是我想要的。我有兴趣做-我想让数据库执行不同的代码,而不是程序):
MyEfContextContainer db = new MyEfContextContainer();
IQueryable<string> uniqueFirstNames =
db.People
.Where(x=> x.GroupId == 42)
.DistinctBy(c=> c.FirstName)
.Select(c=> c.FirstName);
从我可以知道EF/LINQ to Entities如何处理DistinctBy扩展方法的角度来看,调用DistinctBy时会执行存储查询,并且检索数据库中与Where匹配的所有项的列表,然后C#从IE中返回一个IEnumberable与发送给DistinctBy的表达式匹配的DistinctBy方法。
如果列表中有数百万个名称,则效率很低。
我对能够有效地执行此操作感兴趣,希望通过使商店查询仅返回表中所有唯一的名字的结果集。例如,我可能想将IQueryable作为存储库的一部分返回,由于性能原因,由DistinctBy抓取并处理数百万个项目以仅返回唯一值是不可行的。这会将请求处理时间增加到无法接受的水平。
有什么办法吗?我想念什么吗?这只是一个简单的示例,显然,在实际应用程序中,比字符串更复杂的对象将成为对存储库的查询的主题。
最佳答案
我写了这个扩展名:
public static IQueryable<TSource> DistinctBy<TSource, TKey> (this IQueryable<TSource> source, Expression<Func<TSource, TKey>> keySelector)
{
return source.GroupBy(keySelector).Select(x => x.FirstOrDefault());
}
根据属性做出不同的选择,例如ID,我只是调用:
res = res.DistinctBy(x => x.Id);