代码之家  ›  专栏  ›  技术社区  ›  fishhead

查看日期列表的最快方法

  •  4
  • fishhead  · 技术社区  · 16 年前

    我有一个机器工作过的日期列表,但不包括机器停机的日期。我需要创建一个工作日和未工作日的列表。我不知道最好的办法。我已经开始在一个范围内的所有日期中递增,并通过每次遍历整个列表来检查日期是否在列表中。我在寻找一种更有效的方法来寻找日期。

    class machineday
    {
     datetime WorkingDay;
    }
    
    class machinedaycollection : List<machineday>
    {
    public List<TimeCatEvent> GetAllByCat(string cat)
    {
      _CategoryCode = cat;
    
    
      List<machineday> li = this.FindAll(delegate(machinedaydummy) { return true; });
      li.Sort(sortDate);
      return li;
    }
    
    int sortDate(machinedayevent1, machinedayevent2)
    {
      int returnValue = -1;
      if (event2.date < event1.date)
      {
        returnValue = 0;
      }
      else if (event2.date == event1.date)
      {
        //descending
        returnValue = event1.date.CompareTo(event2.date);
      }
      return returnValue;
    }
    }
    
    5 回复  |  直到 16 年前
        1
  •  6
  •   dtb    16 年前

    List<DateTime> days = ...;
    days.Sort();
    DateTime dt = days[0].Date;
    for (int i = 0; i < days.Length; dt = dt.AddDays(1))
    {
        if (dt == days[i].Date)
        {
            Console.WriteLine("Worked: {0}", dt);
            i++;
        }
        else
        {
            Console.WriteLine("Not Worked: {0}", dt);
        }
    }
    

    (假设列表中没有重复的天数。)

        2
  •  3
  •   Marcelo Cantos    16 年前

    建立一个有效日期列表,并使用LINQ的 Enumerable.Except

    IEnumerable<DateTime> dates = get_candidate_dates();
    var holidays = dates.Except(machinedays.Select(m => m.WorkingDay));
    

    这个 get_candidate_dates() 方法甚至可以是一个迭代器,它动态地生成一个范围内的所有日期,而不是预先存储的所有日期列表。

        3
  •  3
  •   Daniel Dolz    16 年前

    抱歉,伙计们,我不太喜欢你们的解决方案。 我认为你应该创建一个包含日期的哈希表。你可以通过在工作日只进行一次互动来做到这一点。

    然后,使用

    myHashTable.ContainsKey(day); // this is efficient
    

    简单、优雅、快捷。

    我认为你的解决方案使用指数时间,这个是线性或对数(这实际上是一件好事)。

        4
  •  0
  •   Zach Smith    16 年前

    假设列表已排序,并且机器大部分时间都在“工作”,则可以通过按月份分组日期并跳过其间的日期来避免迭代所有日期。像这样的事情(你需要清理):

    int chunksize = 60; // adjust depending on data
    machineday currentDay = myMachinedaycollection[0];
    
    for (int i = 0; i < myMachinedaycollection.Count; i += chunksize)  
    {  
        if (currentDay.WorkingDay.AddDays(chunksize) != myMachinedaycollection[i + chunksize].WorkingDay)  
        {
            // write code to iterate through current chunk and get all the non-working days  
        }
        currentDay = myMachinedaycollection[i + chunksize];  
    }  
    
        5
  •  0
  •   Ben Voigt    16 年前

    我怀疑你想要一份工作日和不工作日的清单。

    服务时间排序。对于第一个问题,请执行二进制搜索以查找您关心的日期,并检查前面的条目是否是正在脱机维护或重新投入使用的系统。对于%的正常运行时间,将(停机进行维护,服务已恢复)成对计算,使用减法计算维护持续时间,将这些加起来。然后用减法求总间隔的长度。