[Leetcode学习-java]Merge Intervals

问题:

难度:medium

说明:

输入二维数组 intervals,数组每个元素 int[] 都代表一个区间 [start, end],把重叠的合并,相互接触的不合并,输入的区间是无序的。

题目连接:https://leetcode.com/problems/merge-intervals/

输入范围:

  • 1 <= intervals.length <= 104
  • intervals[i].length == 2
  • 0 <= starti <= endi <= 104

输入案例:

Example 1:
Input: intervals = [[1,3],[2,6],[8,10],[15,18]]
Output: [[1,6],[8,10],[15,18]]
Explanation: Since intervals [1,3] and [2,6] overlaps, merge them into [1,6].

Example 2:
Input: intervals = [[1,4],[4,5]]
Output: [[1,5]]
Explanation: Intervals [1,4] and [4,5] are considered overlapping.

我的代码:

这个比较简单,可以选择排序一遍,然后再进行比较处理,效率较差。不过不排序的话,可以用一个类似于刻度一样的 map 来暂存每一个区间的占有位置,然后进行处理。

class Solution {
    public int[][] merge(int[][] intervals) {
        int[] map = new int[10001];
        int len = intervals.length, index = 0, max = 0;
        
        for(int i = 0;i < len;i ++) {
            boolean flag = true;
            int[] arr = intervals[i];
            max = Math.max(max, arr[1]); // 做区间限制,不过多遍历
            if(map[arr[0]] == 0) 
                map[arr[0]] = 2; 
            else 
                flag = false;
            
            for(int j = arr[0] + 1;j <= arr[1];j ++) {
                flag = map[j] == 0;
                map[j] = 1;
            }
        }
        for(int i = 0;i <= max;) {
            if(map[i] == 2) {
                intervals[index][0] = i;
                while(i <= max && map[++ i] == 1); // 遍历区间
                intervals[index ++][1] = i - 1;
            } else i ++;
        }
        // 结果集
        int[][] res = new int[index][2];
        for(int i = 0;i < index; i ++) {
            res[i] = intervals[i];
        }
        return res;
    }
}

如果用排序的话,代码比较清晰

class Solution {
    public int[][] merge(int[][] intervals) {
        int len = intervals.length, len2 = 1, index = 0;
        Arrays.sort(intervals, new Comparator<int[]>() { // arr[0]升序
            @Override
            public int compare(int[] o1, int[] o2) {
                if (o1[0] == o2[0]) return o1[1] - o2[1];
                return o1[0] - o2[0];
            }
        });
        for(int i = 1;i < len;i ++) {
            int[] arr = intervals[i];
            int[] pre = intervals[i - 1];
            if(arr[0] <= pre[1]) {
                arr[0] = pre[0];
                arr[1] = Math.max(arr[1], pre[1]); // 这里得要比较
                pre[0] = pre[1] = -1;
            } else len2 ++;
        }
        // 结果集
        int[][] res = new int[len2][2];
        for(int i = 0;i < len; i ++) 
            if(intervals[i][0] != -1)  res[index ++] = intervals[i];
        return res;
    }
}

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值