LC 759. Employee Free Time 【lock, hard】

We are given a list schedule of employees, which represents the working time for each employee.

Each employee has a list of non-overlapping Intervals, and these intervals are in sorted order.

Return the list of finite intervals representing common, positive-length free time for all employees, also in sorted order.

Example 1:

Input: schedule = [[[1,2],[5,6]],[[1,3]],[[4,10]]]
Output: [[3,4]]
Explanation:
There are a total of three employees, and all common
free time intervals would be [-inf, 1], [3, 4], [10, inf].
We discard any intervals that contain inf as they aren't finite.

Example 2:

Input: schedule = [[[1,3],[6,7]],[[2,4]],[[2,5],[9,12]]]
Output: [[5,6],[7,9]]

(Even though we are representing Intervals in the form [x, y], the objects inside are Intervals, not lists or arrays. For example, schedule[0][0].start = 1, schedule[0][0].end = 2, and schedule[0][0][0] is not defined.)

Also, we wouldn't include intervals like [5, 5] in our answer, as they have zero length.

Note:

  1. schedule and schedule[i] are lists with lengths in range [1, 50].
  2. 0 <= schedule[i].start < schedule[i].end <= 10^8.

先把所有interval merge 然后找出补集。时间复杂度O(n*log(n))因为有排序这一个操作。

Runtime 60ms,beats 18.06% (看来有更好的做法)

class Solution {
public:
    static bool cmp(Interval v1, Interval v2) {
        if (v1.start != v2.start) return v1.start < v2.start;
        return v1.end < v2.end;
    }
    vector<Interval> employeeFreeTime(vector<vector<Interval>>& schedule) {
        vector<Interval> allemp;
        vector<Interval> merged;
        for (int i = 0; i < schedule.size(); i++) {
            for (int j = 0; j < schedule[i].size(); j++) {
                allemp.push_back(schedule[i][j]);
            }
        }
        sort(allemp.begin(), allemp.end(), cmp);
        int start = allemp[0].start;
        int end = allemp[0].end;
        for (auto v : allemp) {
            if (v.start <= end) {
                end = max(end, v.end);
            }
            else {
                merged.push_back(Interval(start, end));
                start = v.start;
                end = v.end;
            }
        }
        merged.push_back(Interval(start, end));
        // for (auto v : merged) {
        //     cout << v.start << " " << v.end << endl;
        // }
        vector<Interval> freetime;
        if (merged.size() == 1) return freetime;
        for (int i = 0; i < merged.size() - 1; i++) {
            freetime.push_back(Interval(merged[i].end, merged[i+1].start));
        }
        return freetime;
    }
};

下面使用最小堆,

时间其实也是 n log(n)的。但runtime beats 99% 

class Solution {
public:
    static bool cmp(Interval v1, Interval v2) {
        if (v1.start != v2.start) return v1.start < v2.start;
        return v1.end < v2.end;
    }
public:
    vector<Interval> employeeFreeTime(vector<vector<Interval>>& schedule) {
        vector<Interval> allemp;
        vector<Interval> merged;
        vector<Interval> v;
        auto compare = [](Interval lhs, Interval rhs) {return lhs.start > rhs.start; };
        priority_queue<Interval, vector<Interval>, decltype(compare)> q(compare);
        for (auto s : schedule) {
            for (auto e : s) q.push(e);
        }
        auto prev = q.top();
        q.pop();
        while (!q.empty()) {
            auto current = q.top();
            q.pop();
            if (prev.end < current.start) {
                v.push_back(Interval(prev.end, current.start));
                prev = current;
            }
            else {
                prev.end = current.end < prev.end ? prev.end : current.end;
            }
        }
        return v;
    }
};
原文地址:https://www.cnblogs.com/ethanhong/p/10145068.html