这是我正在编写的Java书中的一个练习题。基本上,目标是使用compareTo按递增顺序对泛型类型元素的数组进行排序。
我正在尝试使用QuickSort来完成它。这是我的代码:
public static <T extends Comparable<? super T>>
void sort (T[] arr)
{
// If arr is null, empty,
// or only has 1 element,
// it is already sorted
if (arr == null || arr.length == 0
|| arr.length == 1)
return;
// Call overloaded sort method
sort(arr, 0, arr.length - 1);
}
// HELPER METHOD FOR SORT METHOD
public static <T extends Comparable<? super T>>
void sort(T[] arr, int left, int right)
{
// To be used while sorting
int i = left;
int j = right;
// Check if left and
// right indices are out
// of order. If they are,
// nothing can be done
if (right <= left)
return;
// Middle element used
// as pivot
T pivot = arr[(left + (right - left)) / 2];
// temp will be used
// to swap elements later
T temp;
// QuickSort algorithm
while (i <= j)
{
// Look for values on
// the left greater than
// the pivot and values
// on the right smaller
// than the pivot
// When you find both, swap them
while (arr[i].compareTo(pivot) < 0)
{
i++;
}
while (arr[j].compareTo(pivot) > 0)
{
j--;
}
// Check that i hasn't
// passed j already
if (i <= j)
{
// Swap the items
temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
// Move both indices
// to their next position
i++;
j--;
}
}
// Recursive calls to the
// sort method
if (left < j)
sort(arr, left, j);
if (i < right)
sort(arr, i, right);
}
问题是,当我使用以下数组测试时:
String[] wordArray = {"Droplet", "Blueberry", "Elephant",
"Fate", "Apple", "Coconut", "Darjeeling"};
我在以下行获得了StackOverflowError:
while (arr[i].compareTo(pivot) < 0)
然后在这一行重复一些:
sort(arr, i, right);
上面一行的重复错误告诉我它可能与无限递归发生有关,但我不知道为什么会这样。
我也不知道为什么它会在while循环线上抛出错误......看起来我在比较arr [i]和pivot时使用的逻辑是否合适?
答案 0 :(得分:2)
选择枢轴中间元素的行应为:
T pivot = arr[left + (right - left) / 2];
当前代码实际上使用T pivot = arr[right / 2]
,其中索引right / 2
可能小于左,导致从左到右的范围内不存在的数据透视值。
考虑使用小于左到右范围内所有元素值的枢轴值的情况。这可能导致第一个循环提前i
超过right
或甚至超过数组的末尾,这可能导致堆栈溢出或分段错误。