这个调度算法有更好的解决方案吗?

时间:2014-02-26 09:51:02

标签: algorithm

你有N个人。每个人都有一个空闲时间段列表。

例如,人1的空闲时间段可能是[(9,9.5); (11,12.5)]这意味着他在9点到9点30分之间以及11点到12点30分之间有空。

你想要找一个时间段,这样你就可以聚集所有N个人并召开2个小时的会议。

写一个方法:

输入:

  

列表列表,里面的每个列表都是a的空闲时间段列表   人

输出:

  

一个或多个时间段,您可以使用N个人会面   持续2个小时;或者你找不到这样的时间段


我的想法是这样的:

  • 以下列方式合并两个人的时间段列表:如果两个时间段没有重叠,则删除具有早期开始时间的那个;否则,将重叠部分(新时间段)放入新列表中,并删除具有早期开始时间的部分。继续合并。

  • 合并完成后,我们得到一个新的列表,其中包含两个人的时间重叠,然后将其与第三人合并,依此类推,直到所有列表合并为止。

  • 扫描最终合并列表,找出2小时的广告位。

如果假设每个人有M个空闲时间段,则此算法为** O(N * M)。


有更好的解决方案吗?

1 个答案:

答案 0 :(得分:0)

您的输入大小为N * M,因此您无法获得更好的时间复杂度 - 您必须阅读所有输入。


最初我误读了这个问题,并在下面发布了算法;它的时间复杂度仅略大于输入大小(O(nm log nm)),但是当你想要最大限度地增加会议中的人数时,如果他们不能同时满足所有人的情况,则解决了更一般的情况。

1. Merge periods (a, b), (b, c) into (a, c)
2. Forget periods shorter than 2 hours
3. Transform your input into list of 
    (timestamp_of_beginning, person_id, True)
    (timestamp_of_ending - 2 hours, person_id, False)
4. Sort the list by first element of tuple
5. Iterate over the list, with a set A, 
   adding person_id to A on (_, person_id, True),
   and removing on (_, person_id, False). 

   If after processing some item (t, _, _) 
   A has k elements, you can have a meeting of k persons, their ids are in A.

6. The maximal size of A during iteration is the maximal number of persons 
   that can have the meeting.