c# - 从 List<T> 中选择与无法直接在属性上指定的条件相匹配的组

标签 c# linq

我有以下指定数据记录的类

class DataRecord
{
    public double MeasuredValue { get; set; }
    public DateTime MeasurementDate { get; set; }
}

我想选择在一小时范围内(日期无关紧要)拍摄的记录,其中拍摄的记录数最多。

示例:

  1. 测量日期:2019/01/31 11:50
  2. 测量日期:2019/02/02 17:21
  3. 测量日期:2019/03/01 17:59
  4. 测量日期:2019/03/12 10:54
  5. 测量日期:2019/05/28 11:15

预期输出:1, 4, 5(因为在 10:50 - 11:50 范围内进行了 3 次测量)

我想出的代码是

List<DataRecord> records = new List<DataRecord>();
var maxRecordsInAnHour = records.GroupBy(x => x.MeasurementDate.Hour)
                                .Aggregate((g1, g2) => { return g2.Count() > g1.Count() ? g2 : g1; });

此代码返回 2 和 31 和 5(取决于顺序),因为我按 Hour 属性进行分组,并且只是Hour 中具有相同值的记录将被分组。

如何调整我的代码以获得预期的输出?

最佳答案

我将为您的问题提出 2 种解决方案,具体取决于您列表的长度,其中一种会更好。

初始化:

var myList = new List<DataRecord>
{
    new DataRecord
    {
        MeasurementDate = new DateTime(2019, 1, 31, 11, 50, 0)
    },
    new DataRecord
    {
        MeasurementDate = new DateTime(2019, 1, 31, 17, 21, 0)
    },
    new DataRecord
    {
        MeasurementDate = new DateTime(2019, 1, 31, 17, 59, 0)
    },
    new DataRecord
    {
        MeasurementDate = new DateTime(2019, 1, 31, 10, 54, 0)
    },
    new DataRecord
    {
        MeasurementDate = new DateTime(2019, 1, 31, 11, 54, 0)
    },
};

List<DataRecord> result = new List<DataRecord>();

解决方案1:

var minimumMinutes = myList.Min(x => x.MeasurementDate.Hour * 60 + x.MeasurementDate.Minute);
var maximumMinutes = myList.Max(x => x.MeasurementDate.Hour * 60 + x.MeasurementDate.Minute);

for (int minutes = minimumMinutes; minutes < maximumMinutes; minutes++)
{
    var list = myList.Where(x =>
        x.MeasurementDate.Hour * 60 + x.MeasurementDate.Minute <= minutes + 60 &&
        x.MeasurementDate.Hour * 60 + x.MeasurementDate.Minute >= minutes);

    if (result.Count < list.Count())
    {
        result = list.ToList();
    }
}

解决方案2:

foreach (var dataRecord in myList)
{
    var minutes = dataRecord.MeasurementDate.Hour * 60 + dataRecord.MeasurementDate.Minute;
    var before = myList.Where(x =>
        x.MeasurementDate.Hour * 60 + x.MeasurementDate.Minute >= minutes - 60 &&
        x.MeasurementDate.Hour * 60 + x.MeasurementDate.Minute <= minutes).ToList();
    var after = myList.Where(x =>
        x.MeasurementDate.Hour * 60 + x.MeasurementDate.Minute <= minutes + 60 &&
        x.MeasurementDate.Hour * 60 + x.MeasurementDate.Minute >= minutes).ToList();

    if (before.Count > result.Count ||
        after.Count > result.Count)
    {
        result = before.Count > after.Count ? before.ToList() : after.ToList();
    }
}

关于c# - 从 List<T> 中选择与无法直接在属性上指定的条件相匹配的组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56665384/

相关文章:

c# - 如何将 DataRow 转换为字符串数组?

c# - 如何调用 Entity Framework 中返回动态列的存储过程?

c# - 用于测试多个项目并可能放弃的并行模式

c# - 为 List<Enum> 构建通用方法

c# - ASP.Net MVC5 和 StructureMap4 - 简化方法

c# - 如何根据 LINQ 查询中的选定结果过滤结果?

linq - C# Linq 在多列上连接 2 个表并使用 GROUP BY 进行计数

c# - 在 linq 中指定带有左外连接的计数列

C# 模式搜索

c# - ComboBox 项目的布局