問題の説明
配列intervalは複数の間隔の集合を表し、単一の間隔はintervals [i] = [starti、endi]です。重複するすべての間隔をマージして、重複しない間隔配列を返します。これは、入力のすべての間隔をカバーする必要があります。
例1:
输入:intervals = [[1,3],[2,6],[8,10],[15,18]]
输出:[[1,6],[8,10],[15,18]]
解释:区间 [1,3] 和 [2,6] 重叠, 将它们合并为 [1,6].
例2:
输入:intervals = [[1,4],[4,5]]
输出:[[1,5]]
解释:区间 [1,4] 和 [4,5] 可被视为重叠区间。
促す:
1 <= intervals.length <= 104
intervals[i].length == 2
0 <= starti <= endi <= 104
問題解決のアイデア
間隔の左端で並べ替える場合、並べ替えられたリストで、マージできる間隔は連続している必要があります。または、区間の左端が並べ替えられていない場合、隣接する2つの区間について、次の関係があると見なすこと
ができます.2つの区間の間に5つの関係があることがわかります。間隔並べ替えの場合、関係は3つだけです。
実際、関係1と関係2は重複する関係にマージできますが、関係3は重複しない関係です。
ここで、間隔セットは2次元配列で表されているため、問題は、Javaで指定された条件に従って2次元配列をソートする方法です。
Comparatorインターフェースを実装する必要があるcompareメソッドも同じです。コンパレーターはArrays.sort()関数で渡されます。コンパレーターは匿名の内部クラスを使用して、
Javaの条件に従って2次元配列をソートするためのサンプルコードを実装します。次のように:
public static void main(String[] args) {
// TODO Auto-generated method stub
int [][]matrix={
{
1,3},{
6,8},{
2,6},{
4,7},{
7,19},{
12,18}};
Arrays.sort(matrix,new Comparator<int[]>(){
@Override
public int compare(int[] o1, int[] o2) {
return o1[0]-o2[0];
}
});
for(int i=0;i<matrix.length;i++){
System.out.println("x1="+matrix[i][0]+" x2="+matrix[i][1]);
}
}
動的配列ArrayListコレクションリストを使用して、最終的な回答を保存します。
まず、リスト内の間隔を左端点の昇順で並べ替えます。
続いて、間隔全体がスキャンされ、スキャンプロセス中に、交差する可能性のあるすべての間隔がマージされます。
毎回現在の間隔を維持する必要があり、ループの前に、マージされる間隔の最初の間隔が現在の間隔として使用されます。
-
スキャン時に選択した間隔の左端が現在の間隔の右端より後ろにある場合、それらは重複しません。現在の間隔を結果セットに追加し、現在の間隔をスキャン中に選択した間隔に更新できます。 ;
-
それ以外の場合は重複します。現在の間隔の右端点値をスキャン中に選択した間隔の右端点値と比較し、現在の間隔の右端点値を2つの大きい方の値に設定する必要があります。
実装コード
class Solution {
public int[][] merge(int[][] intervals) {
if(intervals.length==0 ||intervals.length==1){
return intervals;
}
//对区间左端点进行排序
Arrays.sort(intervals,new Comparator<int[]>(){
public int compare(int []o1,int []o2){
return o1[0]-o2[0];
}
});
//创建动态数组用于保存最终结果集
List<int[]> lists=new ArrayList<int[]>();
int start=intervals[0][0],end=intervals[0][1];
int len=intervals.length;
for(int i=1;i<len;i++){
//当选中的区间左端点大于当前区间的右端点时,两区间没有交集
if(intervals[i][0]>end){
//把当前区间左右端点添加到结果集中
int []temp=new int[2];
temp[0]=start;
temp[1]=end;
lists.add(temp);
//更新当前区间左右端点
start=intervals[i][0];
end=intervals[i][1];
//当选中的区间左端点小于等于当前区间的右端点时,两区间有交集
}else{
end=Math.max(intervals[i][1],end);
}
}
//最终还需要把当前区间的左右端点添加到结果集中
int []temp=new int[2];
temp[0]=start;
temp[1]=end;
lists.add(temp);
int reslen=lists.size();
int [][]res=new int[reslen][2];
//把动态数组的结果集加入到二维数组结果集中
for(int i=0;i<reslen;i++){
res[i][0]=lists.get(i)[0];
res[i][1]=lists.get(i)[1];
}
return res;
}
}