如何使用List <igrouping <string,product>&gt;?正确创建分页?

时间:2017-07-17 12:10:21

标签: c# asp.net-mvc entity-framework linq pagination

我有这个查询通过UniqueGroupId

对所有项目进行分组
result = ProductList1.Except(productlist3).Union(ProductList2).GroupBy(a => a.UniqueGroupId).OrderByDescending(a=>a.Key).ToList();

它会返回List<IGrouping<string,Product>>

它工作正常,每个产品都已正确分组,当它找到一个没有设置UniqueGroupId的元素时,它返回一个带有空键的megagroup,其中包含没有正确的UniqueGroupId集的每个产品。

然后将此查询结果提供给显示内容的视图。

现在,由于结果变得越来越大,我想实现分页以便更好地显示内容,其中每个组被计为页面的1个元素,除了具有Key null的组,在此,每个元素该组应被视为1个元素。

我想使用Skip和Take,但显然问题是如果我跳过(50)也会跳过Key null中包含的所有元素,这不是我想要实现的......

我该如何解决这个问题?感谢

2 个答案:

答案 0 :(得分:2)

有点挑战,但可能。

您需要(1)按组合键进行分组,使非空UniqueGroupId生成正常分组,而null UniqueGroupId生成单个元素分组对于每个元素,然后(2)对分组进行排序,(3)应用分页,(4)展平结果,(5)仅通过UniqueGroupId对其进行分组:

var result = ProductList1.Except(productlist3).Union(ProductList2)
    .GroupBy(e => new { K1 = e.UniqueGroupId, K2 = e.UniqueGroupId == null ? e.Id : null }) // (1)
    .OrderBy(g => g.Key.K1).ThenBy(g => g.Key.K2) // (2)
    .Skip(...).Take(...) // 3
    .SelectMany(g => g) // 4
    .GroupBy(e => e.UniqueGroupId); // 5

答案 1 :(得分:0)

您可以对您的群组进行一些重新排序吗?如果是这样,请考虑这个想法:将最大的组放到集合的末尾并重新计算skip计数。这是一个例子:

var result = list.GroupBy(p => p.UniqueGroupId).ToList();

var ordered = result.OrderBy(g => g.Key != null ? 0 : 1);

if (skip < result.Count - 1)
    return ordered.Skip(skip).Take(take);

return ordered.Last().Skip(skip - result.Count - 1)
    .Take(take).GroupBy(p => p.UniqueGroupId);