【问题标题】:How to convert Row to Columns in Linq如何在 Linq 中将行转换为列
【发布时间】:2022-01-26 18:10:20
【问题描述】:

我的表 ReportData 有以下记录

Agency Year Month MonthCount
One 2017 Jan 4
One 2017 Feb 6
One 2017 Nov 29
One 2017 Dec 38
One 2018 Jan 20
One 2019 Feb 18
Two 2017 Jan 24
Two 2017 Feb 66
Three 2017 Nov 9
Four 2017 Dec 8
Four 2018 Jan 22
Four 2019 Feb 48

如何转换成下表?请让我知道 Linq 声明。提前感谢您的帮助。

Agency Month 2017 2018 2019
One Jan 4 20 0
One Feb 6 0 18
One Nov 29 0 0
One Dec 38 0 0
Two Jan 24 0 0
Two Feb 66 0 0
Three Nov 9 0 0
Four Jan 0 22 0
Four Feb 0 0 48
Four Dec 8 0 0

源类结构

    public class ReportingData
{
    public string AgencyName { get; set; }
    public int Year { get; set; }
    public string MonthNumnber { get; set; }
    public string Month { get; set; }
    public int MonthCount { get; set; }
}

【问题讨论】:

  • 我尝试使用数据表进行操作,但现在确定如何使用 Linq。因此,如果有人知道如何编写 Linq 语句或为我指明方向,请提问 - 谢谢!
  • 你能分享你的源类和目标类结构吗?
  • @SateeshPagolu 这里是我的源类 public class ReportingData { public string AgencyName { get;放; } 公共 int 年份 { 获取;放; } 公共字符串 MonthNumber { 获取;放; } 公共字符串月 { 获取;放; } 公共 int MonthCount { 获取;放; } }
  • @SateeshPagolu - 我已将源类添加到问题以便更好地阅读
  • 你也可以添加你的目标类型定义吗?

标签: .net asp.net-mvc linq


【解决方案1】:

在我看来,每个 [Agency, Month] 组合,您需要 2017..2019 年的 MonthCounts。

我想知道你几年后想要什么:只有过去三年?还是 2017 年.. 2025 年?但这是后来的问题。

我的建议是使 ReportData 组具有相同的 [Agency, Month] 组合值。使用 overload of Enumerable.GroupBy that has a parameter resultSelector 精确定义结果。如果您的数据在不同的进程(通常是数据库)中,请使用 IQueryable 版本。

IEnumerable<Report> reportData = ...

// make groups with same values for [Agency, Month] combination
var result = reportData.GroupBy(report => new
{
    Agency = report.Agency,
    Month = report.Month,
},

// parameter resultSelector: for every [Agency, Month] combination,
// and all reports that have this [Agency, Month] combination,
// make one new:
(agencyMonthCombination, reports] => new
{
    Agency = agencyMonthCombination.Agency,
    Month = agencyMonthCombination.Month,

    Year2017 = reports.Where(report => report.Year == 2017)
                      .Select(report => report.MonthCount)
                      .Sum();

    Year2018 = reports.Where(report => report.Year == 2018)
                      .Select(report => report.MonthCount)
                      .Sum();

    Year2019 = reports.Where(report => report.Year == 2018)
                      .Select(report => report.MonthCount)
                      .Sum();

如果您希望每年只有一份报告,则不必求和,您可以使用 FirstOrDefault。

您看到了这种命名年份 2017..2019 的方法的缺点。如果您在所有年份或过去 N 年中编写代码会容易得多:

// parameter resultSelector
(agencyMonthCombination, reports] => new
{
    Agency = agencyMonthCombination.Agency,
    Month = agencyMonthCombination.Month,

    // group the reports with this [Agency, Month] combination in years
    MonthCounts = reports.GroupBy(report => report.Year,

        (year, reportsInThisYear) => new
        {
            Year = year,
            MonthCount = reportsInThisYear.Select(report => report.MonthCount).Sum(),
        })

        // if you only want the last N: orderby descending Year and Take(N)
        .OrderByDescending(yearMonthCount => yearMonthCount.Year)
        .Take(N)

        .ToList(),
    });

【讨论】:

  • 非常感谢 Harald Coppoolse!这正是我想要做的。
猜你喜欢
  • 2019-09-27
  • 2013-08-01
  • 2017-06-28
  • 1970-01-01
  • 2011-11-12
  • 1970-01-01
  • 2013-12-11
  • 2023-03-18
  • 1970-01-01
相关资源
最近更新 更多