合并排序索引越界java

时间:2014-09-30 15:59:20

标签: java sorting mergesort

嘿我正在研究一种合并排序方法,它不断获得索引超出范围的错误。我无法弄清楚为什么或在哪里发生这种情况。我已经尝试打印出指数,看看递归是否有问题,但我不认为这是非常直接的。

public ArrayList<String> mergeSort(ArrayList<String> words,int first, int last){

    if (first < last){
        int mid = (first+ last)/2;
        mergeSort(words,first,mid);
        mergeSort(words,mid+1,last);
        merge(words, first, mid, last);
    }
    return words;

}
public ArrayList<String> merge(ArrayList<String> words, int first, int mid, int last){
    int first1 = first;
    int last1 = mid;
    int first2 = mid+1;
    int last2 = last;
    int total = first1;
    ArrayList<String> temp = new ArrayList<String>();
    while ((first1<=last) && (first2 <= last2)){
        if (words.get(first1).compareTo(words.get(first2))<=0){
            temp.add(total,words.get(first1));
            first1++;
        }
        else{
            temp.add(total,words.get(first2));
            first2++;
        }
        total++;
    }
        while(first1 <= words.size()){
            temp.add(total,words.get(first1));// exception occurs here
        first1++;
        total++;
        }
        while (first2 <= last2){
            temp.add(total,words.get(first2));
            first2++;
            total++;
        }
    for (total = first; total <= last; ++total){
        words.set(total,temp.get(total));
    }
    System.out.println(words);
    return words;
}

2 个答案:

答案 0 :(得分:0)

你的问题是这样的:

temp.set(total,words.get(first1));

你在没有元素的ArrayList上执行此操作。当你调用.set()时,你必须传递一个已经在数组中的元素的索引(即total<temp.size())。

我认为您需要两个临时列表,并且您希望使用ArrayList.add()而不是ArrayList.set()将左半部分的内容放入第一个,而将右半部分放入第二个。然后你可以将它们合并回原来的ArrayList(在这里,你真的可以使用words.set(),因为它已经有了元素,只是顺序错误。)

答案 1 :(得分:0)

您的问题是您在空的临时列表中使用set()set()替换数组中的元素,但数组为空:没有要替换的元素。

您需要做的是add()进入临时列表而不是使用set()。元素将按顺序添加,因此按正确的顺序,您不需要total变量。

现在,当您替换单词中的元素时,它会有所不同。临时列表将包含从0(last - first)的索引元素,并且您希望将firstlast中的元素替换为单词。为此,我认为以下循环将起作用:

for (String word : temp) {
    words.set(first++, word);
}

注意:因为您事先知道临时的最终大小(即last - first + 1),所以您应该使用以下方式预先分配:

ArrayList<String> temp = new ArrayList<String>(last - first + 1);