首页 技术 正文
技术 2022年11月10日
0 收藏 379 点赞 4,171 浏览 1849 个字

归并排序有两种实现方式,自顶向下和自底向上。前者的思想是分治法,现将数组逐级二分再二分,分到最小的两个元素后,逐级往上归并,故其核心在于归并。后者的思想相反,采用循环的方式将小问题不断的壮大,最后变成整个大问题。

归并需要有一个同等大小的辅助数组aux,现将需要归并的元素copy至辅助数组aux中,然后通过逐一比较aux中的元素,将其放至原数组中的合适位置。

归并排序的时间复杂度为nlogn,需要额外的空间n,排序元素稳定,即使在最坏的情况下归并排序的时间复杂度也是nlogn。

 package 排序; import java.util.Arrays; import edu.princeton.cs.algs4.In;
import edu.princeton.cs.algs4.StdOut;
/**
* @author evasean www.cnblogs.com/evasean/
*/
@SuppressWarnings("rawtypes")
public class Merge归并排序 {
private static Comparable[] aux;
private static int num=1;
public static void merge(Comparable[] a, int lo, int mid, int hi){
StdOut.println("merge lo="+lo+",mid="+mid+",hi="+hi);
int i = lo; //左半边元素索引记录
int j = mid+1; //右半边元素索引记录
for(int k = lo; k <= hi; k++)
aux[k] = a[k];
for(int k = lo; k <= hi; k++){
if(i > mid) a[k] = aux[j++];//左半边用尽,取右半边元素
else if(j > hi) a[k] = aux[i++];//右半边用尽,取左半边元素
else if(less(aux[j],aux[i])) a[k] = aux[j++];//右半边当前元素小于左半边当前元素,取右半边元素
else a[k] = aux[i++];//右半边当前元素大于或等于左半边当前元素,取左半边元素
}
StdOut.println("第"+num+"次归并结果:"+Arrays.toString(a));
num++;
}
/**
* 自顶向下的归并排序
* @param a
*/
public static void sort(Comparable[] a){
aux = new Comparable[a.length];
sort(a,0,a.length-1);
}
public static void sort(Comparable[] a, int lo, int hi){
if(hi <= lo) return;
int mid = lo + (hi-lo)/2;
sort(a,lo,mid);
sort(a,mid+1,hi);
merge(a,lo,mid,hi);
}
/**
* 自底向上的归并排序
* @param a
*/
public static void sortBU(Comparable[] a){ int N = a.length;
aux = new Comparable[N];
for(int sz = 1; sz < N; sz=2*sz){
for(int lo = 0; lo < N - sz; lo += 2*sz){
merge(a,lo,lo+sz-1,Math.min(lo+2*sz-1, N-1));
}
}
} @SuppressWarnings("unchecked")
private static boolean less(Comparable v, Comparable w) {
return v.compareTo(w) < 0;
} private static void show(Comparable[] a) {
for (int i = 0; i < a.length; i++)
StdOut.print(a[i] + " ");
StdOut.println();
} public static boolean isSorted(Comparable[] a) {
for (int i = 1; i < a.length; i++) {
if (less(a[i], a[i - 1]))
return false;
}
return true;
} public static void main(String[] args) {
String[] a = new In().readAllStrings();
StdOut.println(Arrays.toString(a));
sort(a);
assert isSorted(a);
show(a);
}
}
相关推荐
python开发_常用的python模块及安装方法
adodb:我们领导推荐的数据库连接组件bsddb3:BerkeleyDB的连接组件Cheetah-1.0:我比较喜欢这个版本的cheeta…
日期:2022-11-24 点赞:878 阅读:9,088
Educational Codeforces Round 11 C. Hard Process 二分
C. Hard Process题目连接:http://www.codeforces.com/contest/660/problem/CDes…
日期:2022-11-24 点赞:807 阅读:5,565
下载Ubuntn 17.04 内核源代码
zengkefu@server1:/usr/src$ uname -aLinux server1 4.10.0-19-generic #21…
日期:2022-11-24 点赞:569 阅读:6,413
可用Active Desktop Calendar V7.86 注册码序列号
可用Active Desktop Calendar V7.86 注册码序列号Name: www.greendown.cn Code: &nb…
日期:2022-11-24 点赞:733 阅读:6,186
Android调用系统相机、自定义相机、处理大图片
Android调用系统相机和自定义相机实例本博文主要是介绍了android上使用相机进行拍照并显示的两种方式,并且由于涉及到要把拍到的照片显…
日期:2022-11-24 点赞:512 阅读:7,822
Struts的使用
一、Struts2的获取  Struts的官方网站为:http://struts.apache.org/  下载完Struts2的jar包,…
日期:2022-11-24 点赞:671 阅读:4,905