Leetcode:为什么这个算法很慢?

时间:2013-09-18 14:23:27

标签: java algorithm

所以我试图解决这个问题:http://oj.leetcode.com/problems/merge-intervals/

我的解决方案是:

public class Solution {

public ArrayList<Interval> merge(ArrayList<Interval> intervals) {
    // Start typing your Java solution below
    // DO NOT write main() function
    // ArrayList<Interval> result = new ArrayList<Interval>();

    //First sort the intervals
    Collections.sort(intervals,new Comparator<Interval>(){
        public int compare(Interval interval1, Interval interval2) {
            if(interval1.start >  interval2.start) return 1;
            if(interval1.start == interval2.start) return 0;
            if(interval1.start <  interval2.start) return -1;
            return 42;
        }
    });

    for(int i = 0; i < intervals.size() - 1; i++){
        Interval currentInterval = intervals.get(i);
        Interval nextInterval = intervals.get(i+1);
        if(currentInterval.end >= nextInterval.start){
            intervals.set(i,new Interval(currentInterval.start,nextInterval.end));
            intervals.remove(i+1);
            i--;
        }
    }

    return intervals;   
}
}

我看过一些博客使用完全相同的解决方案但被接受但我的被拒绝是因为它需要太长时间。你能告诉我为什么需要比预期更长的时间吗? 干杯

编辑:解决,删除太昂贵,使用新的arraylist来存储结果更快

2 个答案:

答案 0 :(得分:2)

最初你要对所有间隔进行排序 - 由于javadocs,这个操作有复杂度O(N * log(N))

但是,之后,正如我所注意到的那样 - 你正在迭代ArrayList,有时会从中删除元素。

但是从ArrayList中删除一些元素有complexity O(N)(因为ArrayList的底层实现是普通数组 - 从数组中间删除任何元素,需要移动该数组的整个右侧部分。)

正如你在循环中所做的那样 - 最后,你的算法的复杂性将是O(N ^ 2)。

我建议你在这种情况下使用LinkedList而不是ArrayList。

答案 1 :(得分:1)

您可以使用一次计算而不是3次比较来改善排序:

Collections.sort(intervals,new Comparator<Interval>(){
    public int compare(Interval interval1, Interval interval2) {
        return interval1.start - interval2.start;
    }
});