题目:
给定一个区间的集合,找到需要移除区间的最小数量,使剩余区间互不重叠。
注意:
可以认为区间的终点总是大于它的起点。
区间 [1,2] 和 [2,3] 的边界相互“接触”,但没有相互重叠。
题解思路:
方法:
1.从区间集合 intvs 中选择一个区间 x,这个 x 是在当前所有区间中结束最早的(end 最小)。这就要对数组end部分排序。
2.把所有与 x 区间相交的区间从区间集合 intvs 中删除。
3.重复步骤 1 和 2,直到 intvs 为空为止。之前选出的那些 x 就是最大不相交子集。
函数代码Java
class Solution {
public int help(int[][] intervals)
{
if(intervals.length==0)
{
return 0;
}
Arrays.sort(intervals, new Comparator<int[]>()
{
public int compare(int[] a, int[] b)
{
return a[1] - b[1];
}
});
int cnt=1;
int end=intervals[0][1];
for(int i=0;i<intervals.length;i++)
{
int start=intervals[i][0];
if(start>=end)
{
cnt++;
end=intervals[i][1];
}
}
return cnt;
}
public int eraseOverlapIntervals(int[][] intervals) {
int n=intervals.length;
int c=help(intervals);
return n-c;
}
}
函数代码C++
版本 1
class Solution {
public:
static bool cmp(vector<int>a,vector<int>b){
return a[1]<b[1];
}
int eraseOverlapIntervals(vector<vector<int>>& intervals) {
int n=intervals.size();
int c=help(intervals);
return n-c;
}
int help(vector<vector<int>>& intervals)
{
if(intervals.size()==0)
{
return 0;
}
sort(intervals.begin(), intervals.end(),cmp);
int x=intervals[0][1];
int cnt=1;
for(int i=0;i<intervals.size();i++)
{
int start=intervals[i][0];
if(start>=x)
{
cnt++;
x=intervals[i][1];
}
}
return cnt;
}
};
版本2:
class Solution {
public:
//sort()必须时静态成员函数
static bool cmp(vector<int>a,vector<int>b){
return a[1]<b[1];
}
int eraseOverlapIntervals(vector<vector<int>>& intervals) {
if (intervals.empty()) return 0;
//按照区间终结点,从小到大排序
sort(intervals.begin(), intervals.end(),cmp);
//获取最小的,区间终结点
int end = intervals[0][1];
int res = 0;
for (int i = 1; i < intervals.size(); ++i) {
//如果区间的起点,小于上一个区间的终点,说明有交集,要删除
if (intervals[i][0] < end) {
++res;
} else {
//没有交集,更新end
end = intervals[i][1];
}
}
return res;
}
};