【问题标题】:How to sort MMMYY on Chart.Js and display the values that match the month?如何在 Chart.Js 上对 MMMYY 进行排序并显示与月份匹配的值?
【发布时间】:2021-08-31 01:09:29
【问题描述】:

这会很长,可能会让人困惑,但请多多包涵。

我之前的问题是我问如何从数据库中提取数据并动态显示在图表中,我已经设法做到了@Rena 的礼貌。这是解决方案https://stackoverflow.com/a/67967555/15397944。 我目前面临一些挑战,我会将我的问题分为两部分,但首先我将展示我的模型设计。

型号

public class payable
{
    public int Id {get; set;}
    public decimal Amount {get; set;}
    public string Month {get; set;}
}

public class receivable
{
    public int Id {get; set;}
    public decimal Amount {get; set;}
    public string Month {get; set;}
}

public class payroll
{
    public int Id {get; set;}
    public decimal Amount {get; set;}
    public string Month {get; set;}
}

public class year
{
    public int Id {get; set;}
    public string Month {get; set;}
}

在数据库中,表在不同月份有不同的值。

例如,如果我在 payable 中调用总金额,按月分组并选择不同月份,我会得到类似

+-------+-------+
| JUL20 | $400  |
+-------+-------+
| SEP20 | $200  |
+-------+-------+
| OCT20 | $300  |
+-------+-------+
| DEC20 | $2000 |
+-------+-------+
| JAN21 | $1910 |
+-------+-------+
| FEB21 | $900  |
+-------+-------+
| MAR21 | $203  |
+-------+-------+
| APR21 | $194  |
+-------+-------+
| MAY21 | $1000 |
+-------+-------+

但如果我对 receivable 做同样的事情,我会得到类似

+-------+-------+
| DEC20 | $1939 |
+-------+-------+
| JAN21 | $191  |
+-------+-------+
| FEB21 | $430  |
+-------+-------+
| MAR21 | $135  |
+-------+-------+
| APR21 | $945  |
+-------+-------+
| MAY21 | $1240 |
+-------+-------+

某些表格中有一些从 2020 年开始的旧月份,但我只希望我的图表显示 2021 年的那些,因此,我创建表格 Year 的原因,只是在 2021 年有 Jan - Present 月份,字符串显示为MMMYY(例如 JAN21)。因此,这在显示图表时给我带来了一个问题,因为我不确定如何仅在 payable.month = year.month 时显示

所以这是第 1 部分,在图表中我只想这样: 其中费用 = 应付 + 工资单。

但我无法做到这对我来说很好,我可以简单地调用所有 3 个并将它们显示在 3 个不同的图表中,这对于我的项目解决方案也可以。

但是,这是第 2 部分。按照解决方案,当我将月份列表的 Handler 方法更改为相应的表或年份表时,我会得到一个混乱的月份(按字母顺序排列),但这意味着其他两张表会排错。

    public JsonResult OnGetRevenueData()
    {
     <!-- Code omitted to shorten -->
        var monthList = _context.year.Select(a => a.Month).Distinct().ToArray();
        return new JsonResult(new { revenue = countRevenue, expense = countExpense, month = monthList });
    }
}

例如,应收账款图表如下所示

因为数据是按照这个 我知道这一点是因为我通过将代码更改为

    public JsonResult OnGetRevenueData()
    {
     <!-- Code omitted to shorten -->
        var monthList = _context.receivable.Select(a => a.Month).Distinct().ToArray();
        return new JsonResult(new { revenue = countRevenue, expense = countExpense, month = monthList });
    }
}

正如您所看到的,它只是跟随数组,所以即使对于第一个图像,其中月份标签跟随年份表,并且我 OrderBy(year.Id) 可以正确地给我 JAN-MAY,值不会跟随,因为 JAN 将是应收的 FEB,然后 FEB 将变为 APR,依此类推。

所以我的问题是,有没有办法实现第 1 部分,其中应收、应付和工资表的月份与图表标签的年份表月份相匹配。否则,是否可以在第 2 部分中代替?

非常感谢您的帮助,感谢您阅读到最后。


编辑:实施解决方案后,数字与 DataTables 和 Database SQL 不一致。

如您所见,对于 DataTables,我对其进行过滤以显示 MAR21,并使用 footerCallback 对 Amount 列中的值求和,从而得出正确的总和

页脚回调代码

"footerCallback": function (row, data, start, end, display) 
{
   var api = this.api(), data;
   var numberRenderer = $.fn.dataTable.render.number(',', '.', 2, '$').display;
// Remove the formatting to get integer data for summation
   var intVal = function (i) 
{
   return typeof i === 'string' ? 
      i.replace(/[\$,]/g, '') * 1 :
         typeof i === 'number' ?
            i : 0;
};

   Total = api
      .column(4, { page: 'current' })
      .data()
      .reduce(function (a, b) {
      return intVal(a) + intVal(b);
      }, 0);
   $(api.column(4).footer()).html(
      'Total : ' + numberRenderer(Total)
   );
}

这是通过使用SQL与数据库本身进行比较来确认它是正确的

但是,在实现图表后的解决方案上,这就是我得到的 图片显示编号为 757210.83。

从截图中也可以看出,MAY 列没有费用,但实际上在数据库中有值。

进一步检查,值 757210.83 属于 May。 因此,这些值求和正确但显示错误。 MAY 数字显示在 MAR 列上,MAR 数字显示在 MAY 列上。其他的也一样 - APR 列上显示 JAN 数字,JAN 列上显示 FEB 数字,FEB 列上显示 APR 数字。所以,我很困惑为什么会这样,它也不是按字母顺序排序的,因为 APR 编号不在 JAN 列中。

但这仍然不能解释缺少的费用列,因为它们都有费用(工资单和/或应付)。

【问题讨论】:

    标签: c# linq asp.net-core chart.js razor-pages


    【解决方案1】:

    你可以像下面这样改变你的 linq:

    public JsonResult OnGetRevenueData()
    {
        var year = _context.year.Select(a => a.Month).ToList();
        var Revenue = (from t in _context.Revenue
                        where year.Contains(t.Month)
                        group t by new {  Month = t.Month} into g                              
                        select new 
                        {
                            Amount = g.Sum(a => a.Amount),
                            Month = g.Key.Month
                        }).ToList();
        var countRevenue = Revenue.OrderBy(a => DateTime.ParseExact(a.Month, "MMMyy", CultureInfo.InvariantCulture).Month)
                                    .Select(a=>a.Amount)
                                    .ToList();
        var countPayroll = (from t in _context.payroll
                            where year.Contains(t.Month)
                            group t by new { Month = t.Month } into g
                            select new {
                                Amount = g.Sum(a => a.Amount),
                                Month = g.Key.Month
                            }).ToList();
        var countPayable = (from t in _context.payable
                            where year.Contains(t.Month)
                            group t by new { Month = t.Month } into g
                            select new
                            {
                                Amount = g.Sum(a => a.Amount),
                                Month = g.Key.Month
                            }).ToList();
          //change here......
        var leftOuterJoin = from a in countPayable
                            join b in countPayroll on a.Month equals b.Month into temp
                            from count in temp.DefaultIfEmpty()
                            select new
                            {
                                Month = a.Month,
                                Amount = a.Amount
                            };
        var rightOuterJoin =
            from b in countPayroll
            join a in countPayable on b.Month equals a.Month into temp
            from count in temp.DefaultIfEmpty()
            select new
            {
                Month = b.Month,
                Amount = b.Amount
            };
        var fullOuterJoin = leftOuterJoin.Union(rightOuterJoin);
        var Expense = (from t in fullOuterJoin
                        group t by new
                        {
                            Month = t.Month
                        } into g
                        select new
                        {
                            Amount = g.Sum(a => a.Amount),
                            Month = g.Key.Month
                        }
                        ).ToList();
        var countExpense = Expense.OrderBy(a => DateTime.ParseExact(a.Month, "MMMyy", CultureInfo.InvariantCulture).Month)
                                    .Select(a => a.Amount)
                                    .ToList();
    
        var yearList = ((from y in _context.year
                            select y.Month
                            )
                        .AsEnumerable()
                        .OrderBy(s => DateTime.ParseExact(s, "MMMyy", CultureInfo.InvariantCulture).Month)
                        ).ToArray();
        return new JsonResult(new { revenue = countRevenue, expense = countExpense, month = yearList });
    }
    

    结果:

    条形图:

    应付表:

    工资表:

    收入表:

    年表:

    【讨论】:

    • 这就像一个魅力,它是惊人的。我不知道该怎么感谢你才足够。我相信这是解决方案,但是奇怪的是图形数字不正确。例如,因为在表格本身中,我使用 DataTables 和 footercallback 函数对列 Amount 求和,例如,Revenue MAR21 在 DataTables 中的总和是 3,197,429.90 美元,但在图表上它只绘制了 757,210.83 美元。真奇怪。
    • 嗨@FlyingSpiderMonkey,嗯,这似乎是另一个问题?你能分享更多细节吗?还有你的数据表是什么?您如何对列的数量求和?
    • 嗨@Rena,我编辑了我的问题来解释为什么总和数字是错误的
    • 好的,我明白了。请检查我的更新答案。
    • 谢谢!!对此感激不尽。它现在终于可以工作了。唯一的问题是缺少五月,这很奇怪,因为所有其他月份的费用都加起来了。 May 还没有工资单,但有一笔应付款项,这有什么不同吗?
    猜你喜欢
    • 2019-06-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-06-29
    相关资源
    最近更新 更多