归并排序用到了递归,归并就是两两合并,然后在此基础上再两两合并,直到合并为一列有序的数据为止。归并排序的时间复杂度为O(N*logN),而冒泡排序、插入排序和选择排序都需要O(N*2)的时间。不过归并排序需要另外一个和待排序数组相同空间大小的数组。
假设归并进行到了最后一步,那么就变成了合并两个有序数组的问题了:
上图显示了合并两个有序数组的示意图,上下两个数组依次从左向右比较元素,谁小就插入中间的目标数组,如果一个数组的元素都以插入目标数组,那么剩下的数组不需要再比较,而是直接按顺序插入目标数组的已有数据的后边。
那么整个过程呢?,大家看下图
上图中就是两两合并,再此基础上再两两合并,谓之二路归并排序是也!
talk is cheap,show me the code:
public class DataArray {
private int[] array;
private int n;
public DataArray(int size){
array = new int[size];
n = 0;
}
public void insert(int value){
array[n++]=value;
}
public void display(){
for(int i=0;i<n;i++){
System.out.println(array[i]+" ");
}
}
public void megerSort(){
int []workSpace = new int[n];
recMegerSort(workSpace,0,n-1);
}
private void recMegerSort(int[] workSpace,int lowerBound,int upperBound){//递归
if(lowerBound==upperBound){
return;
}else{
int mid = (lowerBound+upperBound)/2;
recMegerSort(workSpace,lowerBound,mid);
recMegerSort(workSpace,mid+1,upperBound);
meger(workSpace,lowerBound,mid+1,upperBound);//归并
}
}
private void meger(int[] workSpace,int lowPtr,int highPtr,int upperBound){//归并两个有序数组
int j = 0;
int lowerBound = lowPtr;
int mid = highPtr - 1;
int n = upperBound - lowPtr + 1;
while(lowPtr<=mid&&highPtr<=upperBound){
if(array[lowPtr]<=array[highPtr]){
workSpace[j++] = array[lowPtr++];
}else{
workSpace[j++] = array[highPtr++];
}
}
while(lowPtr<=mid){
workSpace[j++] = array[lowPtr++];
}
while(highPtr<=upperBound){
workSpace[j++] = array[highPtr++];
}
for(int i=0;i<n;i++){
array[lowerBound+i] = workSpace[i];
}
}
}
public class MegeSortDemo {
public static void main(String[] args) {
DataArray da = new DataArray(10);
da.insert(7);
da.insert(11);
da.insert(3);
da.insert(1);
da.insert(23);
da.insert(9);
System.out.println("排序前:");
da.display();
da.megerSort();
System.out.println("排序后:");
da.display();
}
}
运行结果为:
排序前:
7
11
3
1
23
9
排序后:
1
3
7
9
11
23