你有N个人。每个人都有一个空闲时间段列表。
例如,人1的空闲时间段可能是[(9,9.5); (11,12.5)]这意味着他在9点到9点30分之间以及11点到12点30分之间有空。
你想要找一个时间段,这样你就可以聚集所有N个人并召开2个小时的会议。
写一个方法:
输入:
列表列表,里面的每个列表都是a的空闲时间段列表 人
输出:
一个或多个时间段,您可以使用N个人会面 持续2个小时;或者你找不到这样的时间段
我的想法是这样的:
以下列方式合并两个人的时间段列表:如果两个时间段没有重叠,则删除具有早期开始时间的那个;否则,将重叠部分(新时间段)放入新列表中,并删除具有早期开始时间的部分。继续合并。
合并完成后,我们得到一个新的列表,其中包含两个人的时间重叠,然后将其与第三人合并,依此类推,直到所有列表合并为止。
扫描最终合并列表,找出2小时的广告位。
如果假设每个人有M
个空闲时间段,则此算法为** O(N * M)。
有更好的解决方案吗?
答案 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.