Merge sort (merge sort), also known as two-way merge sort, refers to the process of splitting an array into a recursive order for each sub-array, and finally merging the rows into an ordered array. Merge sort is the perfect realization of the application of "divide and conquer law".
From Wikipedia:https://en.wikipedia.org/wiki/merge_sort
1. Merge sort diagram
2. Merge sort process
With the illustration, you can see that the merge sort takes only two steps:
- Divide: Divides the original array into n sub-arrays, each with a length of 1 (an array of length 1 is naturally ordered).
- Merge: Merges two contiguous sequential arrays into an ordered array, repeating operations until an ordered array is left.
3. Code implementation
For a merge sort, the "points" step is nothing special, but the "hop" aspect can do some articles:
Public abstract class Basicmergesort implements sort { @Override public void sort (int[] array) { sort (array, 0, array.length-1); } private void sort (int[] array, int left, int. right) { if (left < right) { int mid = (left + right) >>> 1; Sort (array, left, mid); Sort (Array, mid + 1, right); Merge (array, left, Mid, right); } } protected abstract void Merge (int[] array, int left, int mid, Int. right);}
3.1 Opening additional array space
Merging two ordered arrays (in lengths of N and M) can open a new array of length m+n that can be combined in a linear timeframe.
Public final class MergeSort1 extends Basicmergesort { @Override protected void merge (int[] array, int. left, int m ID, int right) { int[] NewArray = new Int[right-left + 1]; int startIndex1 = left; int startIndex2 = mid + 1; for (int i = 0; i < newarray.length; ++i) { if (startIndex1 = = Mid + 1) { Newarray[i] = array[startindex2++];
} else if (StartIndex2 = = right + 1) { newarray[i] = array[startindex1++]; } else { newarray[i] = Array[s TARTINDEX1] < ARRAY[STARTINDEX2]? Array[startindex1++]: array[startindex2++]; } } System.arraycopy (NewArray, 0, array, left, newarray.length);} }
3.2 Using Direct Insert sorting
Because the arrays that need to be merged are two adjacent parts in the original array, and the first half is ordered, you can use the direct insert sort to complete the merge without using the extra space.
Public final class MergeSort2 extends Basicmergesort { @Override protected void merge (int[] array, int. left, int m ID, int right) {to (int i = mid + 1; I <= right; ++i) { int cur = array[i]; Boolean flag = false; for (int j = i-1, J >= Left,--j) { if (cur < array[j]) { array[j + 1] = Array[j]; } else { array[ J + 1] = cur; Flag = true; break; } } if (!flag) { array[left] = cur; } } }
In general, merging sorts is the first approach to be taken.
4. Time complexity and spatial complexity of merge sorting
4.1 Using extra Space
It is obvious that the number of recursion is M = log2n, and the time consumption of the merge operation is linear, so the time complexity T (n) is as follows:
The time complexity is O (n).
4.2 Using Direct Insert sorting
Space complexity T (n) = O (n^2), with a time complexity of O (1).
5. Performance analysis and optimization of merge sorting
The two algorithms of merging sorting are the strategy of taking space to change time, changing space in time, and its performance has advantages and disadvantages, but the following characteristics can be obtained through analysis:
- The cost of the computer for the frequent opening of fractional space is greater than that of opening up a single array space of equal size.
- Using a direct insert sort (starting at 1/2), the performance is not as large as T (n) = O (log2n) due to a smaller maximum power factor with a small length of n.
Based on the above two properties, a threshold value can be set in the merge sort.
Exceeding this given threshold, the strategy of space-time-change is adopted, and the strategy of time-space-changing is adopted to improve the efficiency of the merging sort.
public class Mixedmergesort implements Sort { private int threshold = 2 << 4; Private Basicmergesort Sort1 = new MergeSort1 (); Private Basicmergesort Sort2 = new MergeSort2 (); public int Getthreshold () { return threshold; } public void Setthreshold (int threshold) { this.threshold = threshold; } @Override public void sort (int[] array) { sort (array, 0, array.length-1); } private void sort (int[] array, int left, int. right) { if (left < right) { int mid = (left + right) >>&G T 1; Sort (array, left, mid); Sort (Array, mid + 1, right); if (Right-left > Threshold) { Sort1.merge (array, left, Mid, right), or else { sort2.merge (array, left, Mid, right);}}}
Source Code:https://github.com/gerrard-feng/algorithm-learning.git
Sorting algorithm 6--Merge sort