检查 List的最快方法约会

发布于 2024-08-28 05:09:36 字数 746 浏览 5 评论 0原文

我有一个机器已运行的日期列表,但它不包括机器停机的日期。我需要创建一个工作天数和未工作天数的列表。我不确定执行此操作的最佳方法。我首先递增一个范围内的所有日期,并通过每次迭代整个列表来检查该日期是否在列表中。我正在寻找一种更有效的方法来查找日期。

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;
}
}

I have a list of dates that a machine has worked on, but it doesn't include a date that machine was down. I need to create a list of days worked and not worked. I am not sure of the best way to do this. I have started by incrementing through all the days of a range and checking to see if the date is in the list by iterating through the entire list each time. I am looking for a more efficient means of finding the dates.

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;
}
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

近箐 2024-09-04 05:09:36

对日期进行排序并迭代结果列表,同时递增计数器。每当计数器与当前列表元素不匹配时,您就会发现列表中缺少一个日期。

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);
    }
}

(这假设列表中没有重复的日期。)

Sort the dates and iterate the resulting list in parallel to incrementing a counter. Whenever the counter does not match the current list element, you've found a date missing in the list.

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);
    }
}

(This assumes there are no duplicate days in the list.)

╄→承喏 2024-09-04 05:09:36

构建有效日期列表,并使用 LINQ 的 Enumerable.Except 扩展方法从中减去机器日集合。类似这样的:

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

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

Enumerable 的方法相当智能,通常会在性能方面做得不错,但如果您想要最快的算法,这将取决于您计划如何使用结果。

Build a list of valid dates and subtract your machine day collection from it using LINQ's Enumerable.Except extension method. Something like this:

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

The get_candidate_dates() method could even be an iterator that generates all dates within a range on the fly, rather than a pre-stored list of all dates.

Enumerable's methods are reasonably smart and will usually do a decent job on the performance side of things, but if you want the fastest possible algorithm, it will depend on how you plan to consume the result.

月下客 2024-09-04 05:09:36

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

方式,对整个日期范围以及在哈希表中查询的每一天(无论日期是否存在)进行交互

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

然后,通过使用简单、优雅和快速的

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

Sorry dudes, but I do not pretty much like your solutions.
I think you should create a HashTable with your dates. You can do this by interating only once the working days.

Then, you interate the full range of of days and for every one you query in the hashtable if the date is there or not, by using

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

Simple, elegant and fast.

I think your solution uses an exponencial time, this one is lineal or logarithmical (which is actually a good thing).

情绪操控生活 2024-09-04 05:09:36

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

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];  
}  

Assuming the list is sorted and the machine was "working" most of the time, you may be able to avoid iterating through all the dates by grouping the dates by month and skipping the dates in between. Something like this (you'll need to clean up):

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];  
}  
梦太阳 2024-09-04 05:09:36

我怀疑您想要一份工作天数和不工作天数的列表。

您的问题标题表明您想知道系统是否在特定日期运行。计算正常运行时间百分比似乎也是合理的。这些都不需要构建间隔中所有时刻的列表。

对服务时间进行排序。对于第一个问题,对您关心的日期进行二分查找,检查前面的条目是否是系统正在下线维护或重新投入使用。对于正常运行时间百分比,将(因维护而停机、服务已恢复)两两进行,使用减法求出维护的持续时间,然后将它们相加。然后用减法求出总间隔的长度。

如果您的问题实际上并不意味着您正在跟踪维护间隔(或等效的使用间隔),那么您可以忽略此答案。

I doubt you want a list of days working and not working.

Your question title suggests that you want to know whether the system was up on a particular date. It also seems reasonable to calculate % uptime. Neither of these requires building a list of all time instants in the interval.

Sort the service times. For the first question, do BinarySearch for the date you care about and check whether the preceding entry was the system being taken offline of maintenance or put back into service. For % uptime, take the (down for maintenance, service restored) pair-wise, use subtraction to find the duration of maintenance, add these up. Then use subtraction to find the length of the total interval.

If your question didn't actually mean you were keeping track of maintenance intervals (or equivalently usage intervals) then you can ignore this answer.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文