EF Core下DistinctBy多属性查询转SQL失败,求等效LINQ写法
EF Core 多属性去重(SQL Server端执行)的可行方案
针对你遇到的DistinctBy无法正确转换为SQL的问题,以下是几种能在SQL Server端执行的等效LINQ查询方案:
方案一:使用EF Core 6+原生DistinctBy(简洁版)
EF Core 6.0及以上版本已支持将DistinctBy转换为SQL。若你的项目符合版本要求,可调整代码如下(用==替代Equals,EF Core对相等运算符的SQL转换更稳定):
var result = Logs .Where(x => x.ProjectCode == projectCode) .OrderByDescending(x => x.SubmittedDate) .DistinctBy(y => new { y.GeographyCode, y.DataSetId });
方案二:分组取最新记录(通用兼容版)
如果你的EF Core版本较低,或DistinctBy仍存在转换问题,可通过分组实现相同逻辑——按GeographyCode和DataSetId分组后,取每组中SubmittedDate最新的记录:
var result = Logs .Where(x => x.ProjectCode == projectCode) .GroupBy(x => new { x.GeographyCode, x.DataSetId }) .Select(g => g.OrderByDescending(x => x.SubmittedDate).FirstOrDefault());
方案三:窗口函数实现(高性能版)
针对大数据量场景,使用ROW_NUMBER()窗口函数的性能更优,EF Core可直接将其转换为对应SQL:
var result = Logs .Where(x => x.ProjectCode == projectCode) .Select(x => new { Log = x, RowNumber = EF.Functions.RowNumber() .Over( PartitionBy: new { x.GeographyCode, x.DataSetId }, OrderByDescending: x.SubmittedDate ) }) .Where(item => item.RowNumber == 1) .Select(item => item.Log);
方案说明
- 方案一最简洁,但依赖EF Core 6.0+版本;
- 方案二兼容性最强,代码易读,适合中小数据量场景;
- 方案三性能最优,适合数据量较大的业务场景。
内容的提问来源于stack exchange,提问作者Purushottam Gupta
相关产品推荐
相关产品推荐

