归并排序
归并排序是一种经典的分治算法,它将数组分成两个子数组,对每个子数组递归地应用归并排序,最后将两个有序的子数组合并成一个有序的数组。
算法步骤
- 将待排序的数组从中间位置分成两个子数组,分别对这两个子数组递归地进行归并排序。
- 将两个排好序的子数组合并成一个有序的数组。合并过程中,需要使用另外一个临时数组来存储合并后的结果。
- 重复步骤2,直到所有的子数组都被合并为一个有序的数组。
基本实现
Golang版
func merge(nums1, nums2 []int) []int {
result := make([]int, 0)
for len(nums1) > 0 || len(nums2) > 0 {
if len(nums1) == 0 {
return append(result, nums2...)
} else if len(nums2) == 0 {
return append(result, nums1...)
} else if nums1[0] < nums2[0] {
result = append(result, nums1[0])
nums1 = nums1[1:]
} else {
result = append(result, nums2[0])
nums2 = nums2[1:]
}
}
return result
}
func mergeSort(nums []int) []int {
if len(nums) <= 1 {
return nums
}
mid := len(nums) / 2
return merge(mergeSort(nums[:mid]), mergeSort(nums[mid:]))
}
Java版
private static int[] mergeSort(int[] nums) {
if (nums.length <= 1) {
return nums;
}
int mid = nums.length / 2;
int[] leftNums = Arrays.copyOfRange(nums, 0, mid);
int[] rightNums = Arrays.copyOfRange(nums, mid, nums.length);
return merge(mergeSort(leftNums), mergeSort(rightNums));
}
private static int[] merge(int[] leftNums, int[] rightNums) {
int[] result = new int[leftNums.length + rightNums.length];
int idx = 0, idx1 = 0, idx2 = 0;
while (idx1 < leftNums.length || idx2 < rightNums.length) {
if (idx1 == leftNums.length) {
result[idx] = rightNums[idx2];
idx2++;
} else if (idx2 ==rightNums.length) {
result[idx] = leftNums[idx1];
idx1++;
} else if (leftNums[idx1] > rightNums[idx2]) {
result[idx] = rightNums[idx2];
idx2++;
} else {
result[idx] = leftNums[idx1];
idx1++;
}
idx++;
}
return result;
}