插入区间
题目描述:
给你一个 无重叠的,按照区间起始端点排序的区间列表。在列表中插入一个新的区间,你需要确保列表中的区间仍然有序且不重叠(如果有必要的话,可以合并区间)。提示:0 <= intervals.length <= 10^4intervals[i].length == 20 <= intervals[i][0] <= intervals[i][1] <= 10^5intervals 根据 intervals[i][0] 按 升序 排列newInterval.length == 20 <= newInterval[0] <= newInterval[1] <= 10^5
class Solution {
public int[][] insert(int[][] intervals, int[] newInterval) {
List<int[]> result = new ArrayList<int[]>();
int len = intervals.length;
if(len == 0){
// 特殊判断
int[][] temp = new int[1][2];
temp[0] = newInterval;
return temp;
}
for(int i = 0 ; i<len ; i++){
int x = intervals[i][0];
int y = intervals[i][1];
if(newInterval[0]<=y && newInterval[0]>=x){
// 插入区间左边界位于区间之间
newInterval[0] = x;
newInterval[1] = (newInterval[1]>y)?newInterval[1]:y;
while(i+1<len && newInterval[1]>=intervals[i+1][0]){
newInterval[1] = intervals[i+1][1]>newInterval[1]?intervals[i+1][1]:newInterval[1];
i++;
}
result.add(newInterval);
}else if(x>newInterval[0] && newInterval[1]>=x){
// 插入边界区间位于区间之前
newInterval[1] = (newInterval[1]>y)?newInterval[1]:y;
while(i+1<len && newInterval[1]>=intervals[i+1][0]){
newInterval[1] = (newInterval[1]>intervals[i+1][1])?newInterval[1]:intervals[i+1][1];
i++;
}
result.add(newInterval);
}else if(i+1<len && y<newInterval[0] && newInterval[1]<intervals[i+1][0]){
result.add(intervals[i]);
result.add(newInterval);
}else if(i == 0 && x>newInterval[1]){
// 第一个作为插入的情况
result.add(newInterval);
result.add(intervals[i]);
}else if(i == len-1 && newInterval[0]>intervals[i][1]){
// 最后一个作为插入的情况
result.add(intervals[i]);
result.add(newInterval);
}else{
// 需要跳过的区间
result.add(intervals[i]);
}
}
return result.toArray(new int[result.size()][2]);
}
}
首先在草稿纸上简单分析可以知道,我们可以将插入合并分为两种情况,一种是待插入区间的左边界位于当前遍历的区间左边界的左边,还有一种是待插入区间的左边界位于当前遍历的区间之间。对于第一种情况:我们要连续考虑左边界问题;对于第二种情况,同样要考虑左边界连续问题。如果这两种情况都未发生,则说明该区间一定位于遍历区间之外,就又有三种情况:一种就是位于两个遍历区间之间,无重叠;一种就是位于第一个遍历区间之前,无重叠;最后一种就是位于最后一个遍历区间之后,无重叠;当以上所以情况都未发生时,则只需要当前的遍历区间加入结果集即可。