首页 > 解决方案 > Linq 按连接表中的项目计数分组

问题描述

我浏览了一堆答案,并试图让代码正常工作,但看不到按 _productBundlesItemsRepository 表分组的方法

这是我正在查看的查询

return _productBundlesRepository.Table.Join(_productBundleItemsRepository.Table,
                    pbr => pbr.Id,
                    pbir => pbir.BundleId,
                    (pbr, pbir) => new { Bundle = pbr, BundleItem = pbir})
                .Where(x => x.BundleItem.ProductId == productId && x.BundleItem.Visible == true && x.Bundle.Active == true).Select(x => x.Bundle).ToList();

我想也许我可以做这样的事情, .OrderByDescending(x => x.BundleItem.Count())但该选项不可用

我还尝试了一些方法,例如在这样的新语句中获取链接到捆绑包的项目数

new { Bundle = pbr, BundleItem = pbir, Count = GetProductBundleItems(pbr.Id).Count})

但后来我收到这样的错误

System.NotSupportedException:LINQ to Entities 无法识别方法“System.Collections.Generic.List”

不太确定我如何订购捆绑包中包含的捆绑包项目数量返回的捆绑包。

更新我根据@StriplingWarrior 的答案使用了一些修改过的代码,但似乎这不起作用,因为多个捆绑包可以包含相同的项目。即一个捆绑包是 2 包,另一个捆绑包是 4 包,两者都使用相同的物品。这是我更新的代码

var bundleItems = _productBundleItemsRepository.Table
                .Where(bundleItem => bundleItem.ProductId == productId
                                     && bundleItem.Visible == true);
            return _productBundlesRepository.Table
                .Select(bundle => new BundleWithCount { pb = bundle, count = bundleItems.Count(bundleItem => bundleItem.BundleId == bundle.Id) })
                .Where(x => x.pb.Active == true && x.count > 0).OrderByDescending(x => x.count).Select(x => x.pb)
                .ToList();

internal class BundleWithCount
    {
        public int count { get; set; }

        public ProductBundle pb { get; set; }
    }

任何人都看到我可能会出错的地方吗?

谢谢

标签: c#sqllinq

解决方案


当您不想从两个表中获取标量数据时,Join 并不是很好。像这样的东西对于获得捆绑包会更有效。

return _productBundlesRepository.Table
    .Where(bundle => bundle.Active == true
        && _productBundleItemsRepository.Table
            .Any(bundleItem => bundleItem.BundleId == bundle.Id
                 && bundleItem.ProductId == productId 
                 && bundleItem.Visible == true))
    .ToList();

或者,换一种说法:

var bundleItems = _productBundleItemsRepository.Table
    .Where(bundleItem => bundleItem.ProductId == productId 
        && bundleItem.Visible == true);
return _productBundlesRepository.Table
    .Where(bundle => bundle.Active == true
        && bundleItems.Any(bundleItem => bundleItem.BundleId == bundle.Id))
    .ToList();

然后,如果您想要每个捆绑包的捆绑商品数量:

var bundleItems = _productBundleItemsRepository.Table
    .Where(bundleItem => bundleItem.ProductId == productId 
        && bundleItem.Visible == true);
return _productBundlesRepository.Table
    .Select(bundle => new BundleWithCount {bundle, count=bundleItems.Count(bundleItem => bundleItem.BundleId == bundle.Id)})
    .Where(x => x.bundle.Active == true && x.count > 0)
    .ToList();

(您需要定义BundleWithCount类,以便可以基于该类型的对象返回泛型)


推荐阅读