0

主要目标是根据受欢迎程度(根据有多少人最喜欢的特定成分表示)以排序顺序返回成分列表。SQL 等价物如下:

select distinct COUNT(PersonalInfoes.FavoriteIngredient_ID) as NoUsing, 
Ingredients.Name 
from PersonalInfoes  right join Ingredients
on PersonalInfoes.FavoriteIngredient_ID = Ingredients.ID
group by Ingredients.Name
order by NoUsing desc

产生与上述相同结果的方法语法的等效 SQL 查询是什么?我得到的最接近的是:

from i in db.Ingredients 
join p in db.PersonalInfos on i.ID equals p.FavoriteIngredient.ID into ing
from p in ing.DefaultIfEmpty()
group i by i.Name into g
from p in g
orderby g.Count() descending
select new { Name = g.Key, Count = g.Count() }.Name;
4

1 回答 1

2

您的查询执行左外连接以包含没有收藏夹的成分。问题是,对于没有收藏夹的每种成分,您都在计算 DefaultIfEmpty() 生成的单个值。您可以在计算时排除默认值,如下所示:

orderby g.Count(x => x != null) descending

您实际上不必执行左连接。您可以将组加入的组数相加:

from i in db.Ingredients 
join p in db.PersonalInfos on i.ID equals p.FavoriteIngredient.ID into faves
group faves.Count() by i.Name into faveCounts
let count = faveCounts.Sum()
orderby count descending
select new { Name = faveCounts.Key, Count = count };

您的代码的一个主观问题是它与所有group byandfrom子句都非常混乱。如果您发现这是一个问题,您可以尝试使用更具描述性的名称、使用子查询或使用方法语法。

编辑:这是一个方法语法版本。它不是从查询语法版本的直接转换,因为那会非常难看。

db.Ingredients
  .GroupJoin(db.PersonalInfos,
             i => i.ID,
             p => p.ID, 
             (i, g) => new { i.Name, FaveCount = g.Count() })
  .GroupBy(x => x.Name,
           (key, grp) => new { Name = key, Count = grp.Sum(y => y.FaveCount) })
  .OrderByDescending(x => x.Count);
于 2012-12-04T01:52:48.090 回答