Lambda Linq Iqueryable 组 - 添加另一个分组

Lambda Linq Iqueryable group - add another grouping

我有一种方法可用于根据用户在选择列表中选择的选项生成摘要报告,以计算在一个区域内完成的某种测试的数量,子集位置在日期范围。

数据如下: 按位置完成的测试计数 从 2015 年 2 月 1 日到 2015 年 3 月 1 日

Total  TestType  Location  Region  Division
455    24 Hour   Lab 1     City 1  Division A
28     24 Hour   Lab 2     City 1  Division A
95     24 Hour   Clinic Z  City 2  Division A
189    24 Hour   Clinic Y  City 2  Division A

这是同一时间段不同测试类型的情况:

Total  TestType  Location  Region  Division
285    48 Hour   Lab 1     City 1  Division A
12     48 Hour   Lab 2     City 1  Division A
75     48 Hour   Clinic Z  City 2  Division A
106    48 Hour   Clinic Y  City 2  Division A

现在,用户希望在一份报告中看到 testType 的摘要细分(在 SQL 中,将另一个属性添加到分组依据)。在我的 testTypeId 选择列表中,我使用 0 作为我的 "All" 项目。在一个完美的世界中,如果 testTypeId == 0,我会在 IQueryable 中添加另一个内容,这样我就可以保留相同的私有方法,而不是编写新的查询。

这是我们希望数据在 "ALL" 情况下的样子:

Total  TestType  Location  Region  Division
455    24 Hour   Lab 1     City 1  Division A
285    48 Hour   Lab 1     City 1  Division A
59     12 Lead   Lab 1     City 1  Division A
28     24 Hour   Lab 2     City 1  Division A
12     48 Hour   Lab 2     City 1  Division A
95     24 Hour   Clinic Z  City 2  Division A
75     48 Hour   Clinic Z  City 2  Division A
5      12 Lead   Clinic Z  City 2  Division A
189    24 Hour   Clinic Y  City 2  Division A
106    48 Hour   Clinic Y  City 2  Division A
8      12 Lead   Clinic Y  City 2  Division A

下面的示例显示了我想要添加的内容,但语法告诉我我不能将包含 IGroupingIQueryable 转换为IQueryable.

的目标类型

谁能给我指出一个好的方向?

private CompletedCountReport GetCompletedCountsByRegion(int regionId, DateTime? startDate, DateTime? endDate, int testTypeId)
{
    var ccRpt = new CompletedCountReport { CompletedCounts = new List<CompletedCount>(), StartDate = startDate, EndDate = endDate, SelectedRegionID = regionId};

    var query = HolterTestDao.FindAll(new GetCompletedByRegionIdAndDates(regionId, startDate.Value, endDate.Value));

    // a specific test type was selected
    if (testTypeId > 0)
    {
        query = query.Where(x => x.HolterTestType == testTypeId);
    }
    // THIS IS WHAT I WANT TO ADD -> otherwise group by test type  <-  THIS IS WHAT I WANT TO ADD.
    if (testTypeId == 0)
    {
        query = query.GroupBy(x => x.HolterTestType);
    }
    // order by locationID within the region.
    query = query.OrderBy(x => x.Location.ID);

    var htList = query.ToList();

    // now Group by Location, to get counts. 
    var reportContents = htList.GroupBy(x => x.Location.ID);
    foreach (var r in reportContents)
    {
        var rList = r.ToList();

        var cc = new CompletedCount();
        var loc = LocationDao.FindById(r.Key);
        cc.Description = loc.Description;
        cc.RegionId = loc.Region.ID;
        cc.DivisionId = loc.Region.Division.ID;
        cc.TestTypeId = testTypeId;
        cc.Count = rList.Count;
        ccRpt.CompletedCounts.Add(cc);
    }

    return ccRpt;
}

我的解决方案是 OrderBy Location 和 HolterTestType,然后是基本内容的 GroupBy 位置,然后在我的循环中通过结果添加另一个分组以按测试类型获取计数:

        query = query.OrderBy(x => x.Location.ID).ThenBy(x => x.HolterTestType);
        var htList = query.ToList();

        // now Group by Location. 
        var reportContents = htList.GroupBy(x => x.Location.ID);

        foreach (var r in reportContents)
        {
            //Group by TestType, to get counts.
            var t = r.GroupBy(x => x.HolterTestType);
            var tList = t.ToList();

            foreach(var u in tList)
            {
                var cc = new CompletedCount();
                var loc = LocationDao.FindById(r.Key);
                cc.Description = loc.Description;
                cc.RegionId = loc.Region.ID;
                cc.DivisionId = loc.Region.Division.ID;
                cc.TestTypeId = u.Key;
                cc.Count = u.Count();
                ccRpt.CompletedCounts.Add(cc);
            }
        }