我的代码出了什么问题?我正在从一个文件中读取数据,该文件每行包含1个数字,并使用合并排序对其进行排序。我收到了以下错误:
Exception in thread "main" java.lang.ArrayIndexOutOfBoundsException: 3
at MergeSort.merge(MergeSort.java:67)
at MergeSort.sort(MergeSort.java:30)
at MergeSort.main(MergeSort.java:86)
TEXTFILE:
300
40
512
234
100
我的mergeSort实现有什么问题吗?
这是我的代码:
import java.io.BufferedReader;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
public class MergeSort
{
void sort(int[] arr, int low, int high)
{
if(high > low)
{
int mid = (low + high)/2;
sort(arr,low,mid);
sort(arr,mid+1,high);
merge(arr, low, mid+1, high);
}
}
void merge(int arr[], int low,int mid, int high)
{
int helper[] = new int[arr.length];
//copy both halves into helper
for(int i=0;i< arr.length;i++)
{
helper[i] = arr[i];
}
//compare elements from left & right, initialize variables
int helperLeft = low;
int helperRight = high;
int curr = mid+1;
//while if left<=mid && mid+1 <=right && if left < right assign lowest elem to original array
while(helperLeft <= curr && curr <=helperRight)
{
if(helperLeft <= curr)
{
arr[helperLeft] = helperLeft;
helperLeft++;
}
else
{
arr[curr] = curr;
curr++;
}
helperRight++;
}
//copy all elements to arr
int rem = mid-helperLeft;
for(int i=0;i<rem;i++)
{
arr[helperRight+i] = helper[helperLeft+i];
}
}
public static void main(String[] args) throws NumberFormatException, IOException {
// TODO Auto-generated method stub
MergeSort pb = new MergeSort();
InputStream inputStream = new FileInputStream("task.txt");
@SuppressWarnings("resource")
BufferedReader R = new BufferedReader(new InputStreamReader(inputStream));
int arraySize = Integer.parseInt(R.readLine());
int[] inputArray = new int[arraySize];
for (int i = 0; i < arraySize; i++) {
inputArray[i] = Integer.parseInt(R.readLine());
}
pb.sort(inputArray, 0, inputArray.length-1);
for (int j = 0; j < inputArray.length; j++) {
System.out.println(inputArray[j]);
}
}
}
新例外:
Exception in thread "main" java.lang.NumberFormatException: null
at java.lang.Integer.parseInt(Unknown Source)
at java.lang.Integer.parseInt(Unknown Source)
at coursera.MergeSort.main(MergeSort.java:74)
答案 0 :(得分:2)
试试这个:
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
public class MergeSort {
public void mergeSort(Integer[] array, int lo, int n) {
int low = lo;
int high = n;
if (low >= high) {
return;
}
int middle = (low + high) / 2;
mergeSort(array, low, middle);
mergeSort(array, middle + 1, high);
int end_low = middle;
int start_high = middle + 1;
while ((lo <= end_low) && (start_high <= high)) {
if (array[low] < array[start_high]) {
low++;
} else {
int Temp = array[start_high];
for (int k = start_high - 1; k >= low; k--) {
array[k + 1] = array[k];
}
array[low] = Temp;
low++;
end_low++;
start_high++;
}
}
}
public static void main(String[] args) throws NumberFormatException, IOException {
MergeSort pb = new MergeSort();
try {
BufferedReader br = new BufferedReader(new FileReader("E:\\task.txt"));
List<Integer> lines = new ArrayList<Integer>();
String line;
while ((line = br.readLine()) != null) {
lines.add(Integer.parseInt(line));
}
br.close();
Integer[] inputArray = lines.toArray(new Integer[lines.size()]);
pb.mergeSort(inputArray, 0, inputArray.length - 1);
for (Integer i : inputArray) {
System.out.println(i);
}
} catch (IOException ie) {
System.out.print(ie.getMessage());
}
}
}
答案 1 :(得分:1)
除了例外,我认为你的merge
逻辑不正确。看看你的代码:
while(helperLeft <= curr && curr <=helperRight)
{
if(helperLeft <= curr)
{
arr[helperLeft] = helperLeft;
helperLeft++;
}
else
{
arr[curr] = curr;
curr++;
}
helperRight++;
}
此处,helperLeft
,helperRight
和curr
都是数组索引。您正在使用索引设置数组元素,例如a[23]=23
。这是不正确的。在MergeSort的合并中,我们应该比较左边和右边的元素并进行合并,而不是索引。
我建议为你的mergesort编写一个unittest,以确保它适用于所有情况(包括极端情况),然后在真实代码中调用你的方法。
如果您的MergeSort.sort()是静态的,也可以。
我也实现了merge(),你可以在这里查看:https://github.com/sk1418/jalgorithm/blob/master/src/main/java/com/kent/algorithm/sorting/MergeSort.java#L130
希望它有所帮助。答案 2 :(得分:0)
我认为问题在于条件
while(helperLeft <= curr && curr <=helperRight)
在此,您永远不会检查helperLeft或helperRight是否超过Array索引。将其修改为folows:
while(helperLeft < arr.length
&& helperRight< arr.length
&& helperLeft <= curr
&& curr <=helperRight)
{
// do something
}