测试数据如下:
Input:
N = 5,arr[] = {4 1 3 9 7}
Output:
1 3 4 7 9
Input:
N = 10,arr[] = {10 9 8 7 6 5 4 3 2 1}
Output:
1 2 3 4 5 6 7 8 9 10
归并排序实现:
public void mergeSort(int n, int[] arr) {
mergeSort(0, n - 1, arr);
}
public void mergeSort(int l, int r, int[] arr) {
if (l >= r) {
return;
}
int mid = (l + r) >> 1;
mergeSort(l, mid, arr);
mergeSort(mid + 1, r, arr);
merge(l, mid, r, arr);
}
public void merge(int l, int m, int r, int[] arr) {
int i = l;
int j = m + 1;
while (i < j && j <= r) {
while (i < j && arr[i] <= arr[j]) {
i++;
}
int index = j;
while (j <= r && arr[j] <= arr[i]) {
j++;
}
swap(arr, i, index - i, j - index);
i += (j - index);
}
}
public void reverse(int i, int j, int[] arr) {
while (i < j) {
int temp = arr[i];
arr[i++] = arr[j];
arr[j--] = temp;
}
}
public void swap(int[] arr, int base, int leftLen, int rightLen) {
reverse(base, base + leftLen - 1, arr);
reverse(base + leftLen, base + leftLen + rightLen - 1, arr);
reverse(base, base + leftLen + rightLen - 1, arr);
}
public static void main(String[] args) {
Homework hw = new Homework();
int[] arr1 = {4, 1, 3, 9, 7};
hw.mergeSort(5, arr1);
System.out.println(Arrays.toString(arr1));
int[] arr2 = {10, 9, 8, 7, 6, 5, 4, 3, 2, 1};
hw.mergeSort(10, arr2);
System.out.println(Arrays.toString(arr2));
}
与常规归并排序中创建额外数组不同的是merge()的实现。
merge构造了两个升序的子数组,且在该范围 [l, r] 内,找到两个连续子数组 [i, mid] 和 [mid+1, j] 满足 arr[i] > arr[j] , i >= l, j <= r,就通过三次反转数组进行原地升序合并。
对调旋转示例:
[ 6 7 8 1 2 3, ......]
0-2,3-5分别实现了升序。
反转0-2,[ 8 7 6 1 2 3 ]
反转3-5,[ 8 7 6 3 2 1 ]
反转0-5,[ 1 2 3 6 7 8 ]