合并排序—排序系列

分治策略

分治策略:将原问题分解成为若干个规模较小而结构与原问题相似地子问题,递归地解决这些子问题,然后再合并其结果,就得到原问题的解。

这形而上的解释并不能让你立刻理解什么是分治?这就像武功秘籍的总纲,只告诉你了这武学的精髓,但是你要能真正理解并运用它还需要具体的招式口诀。要真正掌握分治还得不断地练习,学习一些运用了分治策略地经典算法,就像这合并排序算法。

合并排序算法思想

  1. 将n个元素分成各含n/2个元素的子序列
  2. 递归执行步骤1,直到每个序列元素只有一个
  3. 至下而上地将序列两两排序合并

如何递归地将数组一分为二

俗话说的好,离开代码讲算法都是耍流氓(手动滑稽)。先列出部分代码。

	// n=0,m=10
	public static void sort1(int[] arr,int n,int m){
		if(n<m) {
			int p = (m+n)/2;	   // 语句1
			sort1(arr,n,p);        // 递归1
			sort1(arr,p+1,m);      // 递归2
			merge(arr,n,p,m);      // 这行先不看
		}
	}

这个方法体现了分治策略,将数组不断地一分为二,以n<m为结束条件,当n>=m时说明每个子序列中仅有一个元素。

本方法的实现流程如图所示:
在这里插入图片描述

合并/排序子序列

合并和排序的思想:由于sort方法已经将子序列分割,当然不是实际的分割,只是逻辑上的,传入的参数p,q,r将一段序列分为两份已排序的子序列,把这两个子序列排序合并成一个序列。

合并代码:

public static void merge(int[] arr,int p,int q,int r) {
		int max = Integer.MAX_VALUE;
		int n1 = q-p+1;
		int n2 = r-q;
		int[] L = new int[n1+1];
		int[] R = new int[n2+1];
		for(int i = 0 ;i < n1;i++) {
			L[i] = arr[p+i];
		}
		for(int j = 0;j < n2;j++) {
			R[j] = arr[q+j+1];
		}
		L[n1] = max;
		R[n2] = max;
		int i = 0;
		int j = 0;
		for(int k = p;k <= r;k++) {
			if(L[i] <= R[j]) {
				arr[k] = L[i];
				i++;
			}else {
				arr[k] = R[j];
				j++;
			}
		}
	}

合并排序算法总代码

import java.util.Arrays;

public class Demo8 {
	public static void main(String[] args) {
		int[] arr = new int[] {1,3,5,7,4,2,9,8,10,6};
		Util.sort1(arr,0,9);
		System.out.println(Arrays.toString(arr));
	}
}

class Util{
	public static void merge(int[] arr,int p,int q,int r) {
		int max = Integer.MAX_VALUE;
		int n1 = q-p+1;
		int n2 = r-q;
		int[] L = new int[n1+1];
		int[] R = new int[n2+1];
		for(int i = 0 ;i < n1;i++) {
			L[i] = arr[p+i];
		}
		for(int j = 0;j < n2;j++) {
			R[j] = arr[q+j+1];
		}
		L[n1] = max;
		R[n2] = max;
		int i = 0;
		int j = 0;
		for(int k = p;k <= r;k++) {
			if(L[i] <= R[j]) {
				arr[k] = L[i];
				i++;
			}else {
				arr[k] = R[j];
				j++;
			}
		}
	}
	public static void sort1(int[] arr,int n,int m){
		if(n<m) {
			int p = (m+n)/2;
			sort1(arr,n,p);
			sort1(arr,p+1,m);
			merge(arr,n,p,m);
		}
	}
}

如果有表达错误希望大家能告诉我,对你有帮助地话点个赞哦。

猜你喜欢

转载自blog.csdn.net/weixin_44078014/article/details/105635779