Quicksort算法抛出StackOverflowException

时间:2012-04-15 18:08:54

标签: java algorithm

对于家庭作业,我必须编写QuickSort算法的实现,并使用它以一些随机顺序对包含100k数字的列表进行排序。

在赋值的第一部分中,我必须使用数组的第一项作为pivot元素。这确实返回了一个排序列表。但是,对于赋值的第二部分,我必须使用最后一项作为pivot,这会导致StackOverflowException。当我在8个记录的较小集合中尝试它时,它可以正常工作。我一直在查看我的代码,但我无法弄清楚我在哪里犯了错误。任何帮助将不胜感激。我的代码如下:

public class QuickSort {

    private QuickSortStrategyEnum quickSortStrategy;

    public QuickSort(QuickSortStrategyEnum quickSortStrategy) {

        this.quickSortStrategy = quickSortStrategy;
    }

    public List<Integer> sortIntegerArray(List<Integer> arrayList, int left, int right) {

        if ( left >= right ) {
            return arrayList;
        }

        int i = partition(arrayList, left, right);

        if (i <= right) {

            int pivotNew = partition(arrayList, i, right);
            int pivotIndex = arrayList.indexOf(pivotNew);

            arrayList = sortIntegerArray(arrayList, left , pivotIndex - 1);
            arrayList = sortIntegerArray(arrayList, pivotIndex + 1, right);
        }

        return arrayList;
    }

    private int partition(List<Integer> arrayList, int left, int right) {

        int pivot = getPivot(arrayList, left, right);
        int i = left + 1;

        for (int j = i; j <= right; j++) {

            if (arrayList.get(j) < pivot) {

                Collections.swap(arrayList, j, i);
                i++;
            }
        }

        Collections.swap(arrayList, left, i - 1);
        return i;
    }

    private int getPivot(List<Integer> arrayList, int left, int right) {

        int pivot = 0;

        switch (quickSortStrategy) {

            case FIRST:
            pivot = arrayList.get(left);
            break;

            case LAST:
            pivot = arrayList.get(right);
            break;
        }
        return pivot;
    }

}

3 个答案:

答案 0 :(得分:5)

提示:如果right == left + 1会发生什么?

答案 1 :(得分:1)

这两条线看起来很可疑:

int pivotNew = partition(arrayList, i, right);
int pivotIndex = arrayList.indexOf(pivotNew);

查看partition返回的内容,并将其与您使用结果的方式进行比较。

答案 2 :(得分:1)

除了David Harkness指出的事实,分区逻辑也存在问题。试试这个:(删除David Harkness指出的东西后)

private int partition(List<Integer> arrayList, int left, int right) {

    int pivot = getPivot(arrayList, left, right);
    int i = left - 1; 

    for (int j = left; j < right; j++) {
        if (arrayList.get(j) <= pivot) {
            i++;
            Collections.swap(arrayList, j, i);
        }
    }

    Collections.swap(arrayList, i+1, right);
    return i+1;
}

它适用于pivot是最后一个元素的情况。不是第一个元素。

阅读,理解纸上工作,干出来,编写伪代码,然后向Eclipse打招呼。不要急于实现。