1. 程式人生 > 實用技巧 >435. 無重疊區間

435. 無重疊區間

題目:

給定一個區間的集合,找到需要移除區間的最小數量,使剩餘區間互不重疊。

注意:

可以認為區間的終點總是大於它的起點。
區間 [1,2] 和 [2,3] 的邊界相互“接觸”,但沒有相互重疊。
示例 1:

  輸入: [ [1,2], [2,3], [3,4], [1,3] ]

  輸出: 1

  解釋: 移除 [1,3] 後,剩下的區間沒有重疊。
示例 2:

  輸入: [ [1,2], [1,2], [1,2] ]

  輸出: 2

  解釋: 你需要移除兩個 [1,2] 來使剩下的區間沒有重疊。
示例 3:

  輸入: [ [1,2], [2,3] ]

  輸出: 0

  解釋: 你不需要移除任何區間,因為它們已經是無重疊的了。

解答:

貪心演算法

思路:按照區間結束值的從小到大排序,然後依次判斷當前vec與上一個不重複的vec直接是否有重複,如果有則remove++,最後返回remove的值。

int eraseOverlapIntervals(vector<vector<int>>& intervals) 
{
    if (intervals.size() < 2)
        return 0;

    //定義判斷兩vec是否重疊的函式
    auto isOverlap = [&](vector<int>& vec1, vector<int
>& vec2)->bool { if (vec2[0] >= vec1[0] && vec2[0] < vec1[1]) return true; if (vec1[0] >= vec2[0] && vec1[0] < vec2[1]) return true; return false; }; //定義排序函式:按照結束值的大小進行排序 auto sortVec = [&](vector<int
>& vec1, vector<int>& vec2)->bool { return (vec1[1] < vec2[1]); }; sort(intervals.begin(), intervals.end(), sortVec); /*for (auto val : intervals) { cout << val[0]<<"\t"<<val[1] << endl; } cout << endl;*/ int removeNum = 0; //!!!注意:需要用一個變數記住上次不重複的vec是哪個,因為需要i與上一個區間進行判斷 vector<int>& pre = intervals[0]; for (int i = 1; i < intervals.size(); i++) { if (isOverlap(pre, intervals[i])) { removeNum++; continue; } pre = intervals[i]; } return removeNum; }

動態規劃

TODO

參考:https://leetcode-cn.com/problems/non-overlapping-intervals/solution/wu-zhong-die-qu-jian-by-leetcode/