归并排序非递归算法
1、算法思想
相比于递归的算法,个人觉得非递归更容易理解一些,相比较于递归排序算法需要递归成单个元素然后再合并,非递归直接将他们看成单个元素,分组合并,通过控制每一轮的分组个数来进行归并排序,每次gap的值二倍递增来进行排序,直达gap=array.length表示全部归并完毕,也全部排序完成啦~
2、图解
说的比较ran,大家可以看一下图解
3.实现
//归并排序的非递归
public static void merge2(int[] array,int gap){
int[] tmpArray = new int[array.length];
int i = 0;
int start1 = 0;
int end1 = start1+gap-1;
int start2 = end1 +1;
//因为end2可能只有一个或者两个元素两种情况
int end2 = start2 +gap -1 <= array.length-1 ?
start2+gap-1:array.length-1 ;
while (start2 < array.length) {
//保证有两个归并段
while (start1 <= end1 && start2 <= end2) {
//比较
if (array[start1] <= array[start2]) {
tmpArray[i++] = array[start1++];
} else {
tmpArray[i++] = array[start2++];
}
}
while (start1 <= end1) {
tmpArray[i++] = array[start1++];
}
while (start2 <= end2) {
tmpArray[i++] = array[start2++];
}
//证明一次二路归并已经完成
start1 = end2 + 1;
end1 = start1 + gap - 1;
start2 = end1 + 1;
end2 = start2 + gap - 1 <= array.length - 1 ?
start2 + gap - 1 : array.length - 1;
}
//归并完成后start1后还有数据,直接赋值给tempArray数组
while(start1 < array.length){
tmpArray[i++] = array[start1++];
}
for (int j = 0; j <tmpArray.length ; j++) {
array[j] = tmpArray[j];
}
}
//对步数进行控制
public static void mergeSort2(int[] array){
for (int i = 0; i <array.length -1; i*=2) {
merge2(array,i);
}
}
public static void main1(String[] args) {
int[] array = new int [100];
int[] tmpArray = new int[array.length];
Random random = new Random();
for (int i = 0; i <array.length ; i++) {
array[i] = random.nextInt(100)+1;
}
System.out.println(Arrays.toString(array));
mergeSort2(array);
System.out.println(Arrays.toString(array));
}
}