【问题标题】:How do I select the maximum date count and display如何选择最大日期计数和显示
【发布时间】:2020-05-28 00:09:54
【问题描述】:

我有一个页面,我需要使用数据库表中的最大日期作为标准来显示已过期的交易, 例如: 我的表中有以下日期,另一列中的状态为已过期

13/11/2020
19/05/2017
16/08/2003

我正在选择日期为 2020 年 13 月 11 日(最大日期)且状态为已过期的所有项目,并显示页面中匹配的所有记录的数量。 有没有办法使用 orderbydescending 或任何其他 lambda 或 linq 表达式来实现这一点?

【问题讨论】:

  • 使用 EF 可能是可能的,但我发现编写 FromSqlRaw() 查询更容易。
  • 是的。有可能的。但是,合理吗?不知道! -- 您提供的关于您的应用程序的信息非常少。您的数据源是什么?你有什么数据,你如何得到它,当你想分析它时它是什么形式。你在使用实体框架吗?这一切都必须考虑。

标签: c# asp.net-mvc asp.net-core lambda


【解决方案1】:

在示例中,itemList 是一个 Items 列表,其中包含 int 类型的 ItemIdDateTime 类型的 ItemDatestring 类型的 ItemStatus

此代码为每个 id (ItemId) 获取带有 ma​​x dateexpired 项 (ItemStatus == "Expired") 并将这些元素放置到maxDateForEachExpiredItem列表。

itemList.GroupBy(item => item.ItemId).ToList()
    .ForEach(itemGroup => maxDateForEachExpiredItem.Add(
        itemGroup.ToList()
            .Where(itemGroupElement => itemGroupElement.ItemStatus == "Expired")
            .OrderByDescending(itemGroupElement => itemGroupElement.ItemDate)
            .FirstOrDefault()));

为了获取日期为"13/11/2020"的此类项目的数量

maxDateForEachExpiredItem.Where(item => item.ItemDate == DateTime.Parse("11/13/2020")).Count()

注意DateTime.Parse("11/13/2020") 中的日期格式是月/日/年

说明:

1. itemListItemId 分组。这些项目组被转换为列表以便遍历它们。

itemList.GroupBy(item => item.ItemId).ToList()

2. 遍历 1 部分列表中的每个元素(按 ItemId 分组的项目)并添加一些内容到列表 maxDateForEachExpiredItem

.ForEach(itemGroup => maxDateForEachExpiredItem.Add(

3.ItemId 分组的项目将转换为列表,以便遍历该组。

itemGroup.ToList()

4. 从按ItemId 分组的项目组中,取出ItemStatusExpired 的项目。

.Where(itemGroupElement => itemGroupElement.ItemStatus == "Expired")

5. 从最新日期开始,按ItemDate 订购这些商品。

.OrderByDescending(itemGroupElement => itemGroupElement.ItemDate)

6.最后,从这个有序列表中取出第一项。

.FirstOrDefault()));

这是完整的例子。

using System;
using System.Collections.Generic;
using System.Linq;

namespace ConsoleApp10
{
    class Program
    {
        static void Main(string[] args)
        {
            List<Item> itemList = new List<Item>
            {
                new Item(1, "01/05/2015", "Expired"),
                new Item(1, "01/06/2015", "Expired"),
                new Item(1, "01/12/2020", "Active"),
                new Item(2, "01/03/2015", "Expired"),
                new Item(2, "01/07/2019", "Expired"),
                new Item(2, "01/10/2020", "Active"),
                new Item(2, "13/11/2020", "Expired"),
                new Item(3, "16/08/2003", "Expired"),
                new Item(3, "19/05/2017", "Expired"),
                new Item(3, "13/11/2020", "Expired"),
                new Item(3, "31/12/2020", "Active")
            };

            List<Item> maxDateForEachExpiredItem = new List<Item>();

            itemList.GroupBy(item => item.ItemId).ToList()
                .ForEach(itemGroup => maxDateForEachExpiredItem.Add(
                itemGroup.ToList()
                        .Where(itemGroupElement => itemGroupElement.ItemStatus == "Expired")
                        .OrderByDescending(itemGroupElement => itemGroupElement.ItemDate)
                        .FirstOrDefault()));

            Console.WriteLine("Max date for each expired item:\n");
            foreach (var item in maxDateForEachExpiredItem)
            {
                Console.WriteLine(item);
            }

            Console.WriteLine("\nNumber of items where date is 13/11/2020: " +
            $"{maxDateForEachExpiredItem.Where(item => item.ItemDate == DateTime.Parse("11/13/2020")).Count()}");

            Console.ReadLine();
        }

        private class Item
        {
            public int ItemId { get; set; }
            public DateTime ItemDate { get; set; }
            public string ItemStatus { get; set; }

            public Item(int id, string date, string status)
            {
                ItemId = id;
                string[] dateParts = date.Split('/');
                ItemDate = new DateTime(int.Parse(dateParts[2]), int.Parse(dateParts[1]), int.Parse(dateParts[0]));
                ItemStatus = status;
            }

            public override string ToString()
            {
                return $"ItemId = {ItemId}, ItemDate = {ItemDate.ToString("dd/MM/yyyy")}, ItemStatus = {ItemStatus}";
            }
        }
    }
}

结果

【讨论】:

  • 哇...在顶部。毫无疑问,您为这个答案付出了很多努力,但我们甚至不知道数据的可用形式。您已经对可能不存在的数据做出了假设。就解决方案本身而言——我几乎无法遵循这个例子。除此之外,让我们图像到 OP 有 100.000+ 行数据要处理?这个规模好吗?不——有比这更简单的解决方案。一种不需要两个 List 对象并且不对集合执行一些非常昂贵的操作。
  • 据我了解,OP 想为过期项目选择最大日期,然后根据日期计算此类项目。由于组中需要单个数据(最大日期),因此必须有一些独特的数据,这里表示为ItemId。但我明白你的意思,也许解决方案可能更简单,性能更“重”。解决方案本身很难遵循,还是整个示例难以遵循?
  • OP 声明“我有一个页面,我需要在其中显示过期的交易......”这几乎听起来他们已经查询了数据库并过滤了“过期”......也许很多不是。太多的未知数。 --“我正在选择日期为 2020 年 13 月 11 日(最大日期)的所有项目”这是否意味着他们需要从记录中评估“最大日期”,或者正在选择日期值以及使用可变日期的内容?再次,太多的未知数。
【解决方案2】:
 public class Transactions
 {
    public DateTime Date { get; set; }
    public string Status { get; set; }
 }
class Program
{
    static void Main(string[] args)
    {
        List<Transactions> transactions = new List<Transactions>
        {
            new Transactions {Date = Convert.ToDateTime("13/11/2020") , Status="Expired"},
            new Transactions {Date = Convert.ToDateTime("19/05/2017") , Status="Expired"},
            new Transactions {Date = Convert.ToDateTime("16/08/2003") , Status="Expired"},
            new Transactions {Date = Convert.ToDateTime("13/11/2020") , Status="Expired"},
            new Transactions {Date = Convert.ToDateTime("13/11/2020") , Status="Expired"},
            new Transactions {Date = Convert.ToDateTime("13/11/2020") , Status="Active"},

        };

        var expiredStatusTransactions = transactions.Where(x => x.Status == "Expired")
            .OrderByDescending(x => x.Date);
        if(expiredStatusTransactions.Any())
        {
            var expiredTransactionDetails = expiredStatusTransactions.Where(x => x.Date == expiredStatusTransactions.FirstOrDefault().Date);
            if(expiredTransactionDetails.Any())
            {
                foreach(var details in expiredTransactionDetails)
                {
                    Console.WriteLine($"Date : {details.Date.ToShortDateString()}     Status : {details.Status}");
                }

                Console.WriteLine($"Total Count : {expiredTransactionDetails.Count()}");
                Console.ReadLine();
            }
        }
    }
}

【讨论】:

    猜你喜欢
    • 2019-08-20
    • 1970-01-01
    • 2019-05-27
    • 1970-01-01
    • 1970-01-01
    • 2018-03-22
    • 1970-01-01
    • 2013-07-24
    • 1970-01-01
    相关资源
    最近更新 更多