LINQ 表达式“First()”无法翻译,将在本地进行评估。使用 groupby 时

zaw*_*sza 7 entity-framework-core

升级到 ef core 3.0 后。我在对结果进行分组时遇到问题。如果我删除分组部分它工作正常。但当然我需要得到总和所以需要它。

IQueryable<ShackGapiModel> models = _context.Offers
                .Where(i => i.Amount > 0)
                .Select(o => new ShackGapiModel
                {
                    Id = o.Shack.Id,
                    Title = o.Shack.Title,
                    AmountOnExchange = o.Amount
                })
                .GroupBy(i => i.Id)
                .Select(s => new ShackGapiModel
                {
                    Id = s.First().Id,
                    Title = s.First().Title,
                    AmountOnExchange = s.Sum(a => a.AmountOnExchange)                   
                });
Run Code Online (Sandbox Code Playgroud)

cde*_*dev 4

原因是 EFCore 无法将您的 linq 查询转换为 sql 查询。因此,它将数据存入内存,然后应用您的 linq。这是非常消耗内存的事情。

https://learn.microsoft.com/en-us/ef/core/what-is-new/ef-core-3.0/writing-changes#linq-queries-are-no-longer-evaluated-on-the-客户

缓解措施

如果查询无法完全翻译,则可以以可翻译的形式重写查询,或者使用 AsEnumerable()、ToList() 或类似方法将数据显式带回客户端,然后在客户端进行进一步处理使用 LINQ 到对象。

作为替代方法,当采用组键以外的值时,我更喜欢使用 Max() 。

IQueryable<ShackGapiModel> models = _context.Offers
                .Where(i => i.Amount > 0)
                .GroupBy(i => i.Id)
                .Select(s => new ShackGapiModel
                {
                    Id = = s.Key.Value,
                    Title = s.Max(a => a.title),
                    AmountOnExchange = s.Sum(a => a.AmountOnExchange)                   
                });
Run Code Online (Sandbox Code Playgroud)