归并排序里运用到算法里很重要的一个思想——分治法:将原问题分解为几个规模较小但类似于原问题的子问题——《算法导论》。在每一层递归中都有3个步骤:
1.分解问题
2.解决问题
3.合并问题的解
举例待排序数组:{6, 5, 3, 1, 7, 2, 4},将它原始序列做分解。
可以经过不断的递归分解可以看到已经把原始数组序列不断分解为最小单位,接下来不妨将它们看做是二叉树的叶子节点。
将他们进行两两归并排序形成二叉树(也称为2路归并算法),可见二叉树的根节点即为最终序列。在这个过程中我们完成了剩余的两个步骤:解决问题和合并问题。
理论很简单,实践很“复杂”。对于归并排序的理论从上面的二叉树就看的很明白,将原始待排序数组不断分解最后看成是二叉树的叶子节点,再把它们两两排形成新的节点,逐渐归并为一个节点,此时的节点即为排好序的数组序列。
Java
1 package com.algorithm.sort.merge; 2 3 import java.util.Arrays; 4 5 /** 6 * 归并排序(递归) 7 * Created by yulinfeng on 2017/6/23. 8 */ 9 public class Merge {10 public static void main(String[] args) {11 int[] nums = {6, 5, 3, 1, 7, 2, 4};12 nums = mergeSort(nums);13 System.out.println(Arrays.toString(nums));14 }15 16 /**17 * 归并排序18 * @param nums 待排序数组序列19 * @return 排好序的数组序列20 */21 private static int[] mergeSort(int[] nums) {22 segment(nums, 0, nums.length - 1);23 return nums;24 }25 26 /**27 * 递归切分待排28 * @param nums 待切分数组29 * @param left 待切分最后第一个元素的索引30 * @param right 待切分数组最后一个元素的索引31 */32 private static void segment(int[] nums, int left, int right) {33 if (left >= right)34 return;35 // 找出中间索引36 int center = (left + right) / 2;37 // 对左边数组进行递归38 segment(nums, left, center);39 // 对右边数组进行递归40 segment(nums, center + 1, right);41 // 合并42 merge(nums, left, center, right);43 }44 45 /**46 * 两两归并排好序的数组(2路归并)47 * @param nums 带排序数组对象48 * @param left 左边数组的第一个索引49 * @param center 左数组的最后一个索引,center + 1右数组的第一个索引50 * @param right 右数组的最后一个索引51 */52 private static void merge(int[] nums, int left, int center, int right) {53 int[] tmpArray = new int[nums.length];54 int rightIndex = center + 1; // 右数组第一个元素索引55 int tmpIndex = left; //临时数组索引56 int begin = left; // 缓存左数组第一个元素的索引,用于将排好序的数组拷贝回原数组57 while (left <= center && rightIndex <= right) {58 if (nums[left] <= nums[rightIndex]) {59 tmpArray[tmpIndex++] = nums[left++];60 } else {61 tmpArray[tmpIndex++] = nums[rightIndex++];62 }63 }64 while (left <= center) {65 tmpArray[tmpIndex++] = nums[left++];66 }67 while (rightIndex <= right) {68 tmpArray[tmpIndex++] = nums[rightIndex++];69 }70 while (begin <= right) {71 nums[begin] = tmpArray[begin++];72 }73 }74 }
Python3
1 #二路归并排序(递归) 2 def merge_sort(nums): 3 segment(nums, 0, len(nums) - 1) 4 return nums 5 6 #切分待排序数组 7 def segment(nums, left, right): 8 if left >= right: 9 return10 center = int((left + right) / 2)11 segment(nums, left, center)12 segment(nums, center + 1, right)13 merge(nums, left, center, right)14 15 #两两归并排好序的数组(二路归并)16 def merge(nums, left, center, right):17 tmpArray = [0] * len(nums)18 rightIndex = center + 1 #右数组的第一个元素索引19 tmpIndex = left20 begin = left21 while left <= center and rightIndex <= right:22 if nums[left] <= nums[rightIndex]:23 tmpArray[tmpIndex] = nums[left]24 tmpIndex += 125 left += 126 else:27 tmpArray[tmpIndex] = nums[rightIndex]28 tmpIndex += 129 rightIndex += 130 while left <= center:31 tmpArray[tmpIndex] = nums[left]32 tmpIndex += 133 left += 134 while rightIndex <= right:35 tmpArray[tmpIndex] = nums[rightIndex]36 tmpIndex += 137 rightIndex += 138 while begin <= right:39 nums[begin] = tmpArray[begin]40 begin += 141 42 nums = [6, 5, 3, 1, 7, 2, 4]43 nums = merge_sort(nums)44 print(nums)
以上是比较排序之归并排序(递归)的实例教程的详细内容。更多信息请关注PHP中文网其他相关文章!

是的,C++Lambda表达式可以通过使用std::function支持递归:使用std::function捕获Lambda表达式的引用。通过捕获的引用,Lambda表达式可以递归调用自身。

给定两个字符串str_1和str_2。目标是使用递归过程计算字符串str1中子字符串str2的出现次数。递归函数是在其定义中调用自身的函数。如果str1是"Iknowthatyouknowthatiknow",str2是"know"出现次数为-3让我们通过示例来理解。例如输入str1="TPisTPareTPamTP",str2="TP";输出Countofoccurrencesofasubstringrecursi

我们以整数数组Arr[]作为输入。目标是使用递归方法在数组中找到最大和最小的元素。由于我们使用递归,我们将遍历整个数组,直到达到长度=1,然后返回A[0],这形成了基本情况。否则,将当前元素与当前最小或最大值进行比较,并通过递归更新其值以供后续元素使用。让我们看看这个的各种输入输出场景−输入 −Arr={12,67,99,76,32};输出 −数组中的最大值:99解释 &mi

Python是一门易学易用的编程语言,然而在使用Python编写递归函数时,可能会遇到递归深度过大的错误,这时就需要解决这个问题。本文将为您介绍如何解决Python的最大递归深度错误。1.了解递归深度递归深度是指递归函数嵌套的层数。在Python默认情况下,递归深度的限制是1000,如果递归的层数超过这个限制,系统就会报错。这种报错通常称为“最大递归深度错误

如何使用Vue表单处理实现表单的递归嵌套引言:随着前端数据处理和表单处理的复杂性不断增加,我们需要通过一种灵活的方式来处理复杂的表单。Vue作为一种流行的JavaScript框架,为我们提供了许多强大的工具和特性来处理表单的递归嵌套。本文将向大家介绍如何使用Vue来处理这种复杂的表单,并附上代码示例。一、表单的递归嵌套在某些场景下,我们可能需要处理递归嵌套的

在Linux系统中,“ls”命令是一个非常有用的工具,它提供了对当前目录中文件和文件夹的简洁概述。通过“ls”命令,您可以快速查看文件和文件夹的权限、属性等重要信息。虽然“ls”命令是一个基本的命令,但是通过结合不同的子命令和选项,它可以成为系统管理员和用户的重要工具。通过熟练使用“ls”命令及其各种选项,您可以更高效地管理文件系统,快速定位所需文件,以及执行各种操作。因此,“ls”命令不仅可以帮助您了解当前目录结构,还可以提高您的工作效率。比如,在Linux系统中,通过使用带有递归选项的"ls

注:本文以Go语言的角度来比较研究循环和递归。在编写程序时,经常会遇到需要对一系列数据或操作进行重复处理的情况。为了实现这一点,我们需要使用循环或递归。循环和递归都是常用的处理方式,但在实际应用中,它们各有优缺点,因此在选择使用哪种方法时需要考虑实际情况。本文将对Go语言中的循环和递归进行比较研究。一、循环循环是一种重复执行某段代码的机制。Go语言中主要有三

随着互联网的发展,各种网站和应用程序中都出现了树形结构的展示,例如分类目录、人员组织架构、权限管理等。在这些应用场景中,递归树结构已经成为了非常重要且实用的模型之一。ThinkPHP6是一种基于MVC模型的PHP开发框架,其拥有丰富的扩展库和优秀的性能,广受开发者的认可和使用,而在ThinkPHP6中实现递归树结构也变得更加方便了。下面,我们将介绍如何在Th


热AI工具

Undresser.AI Undress
人工智能驱动的应用程序,用于创建逼真的裸体照片

AI Clothes Remover
用于从照片中去除衣服的在线人工智能工具。

Undress AI Tool
免费脱衣服图片

Clothoff.io
AI脱衣机

AI Hentai Generator
免费生成ai无尽的。

热门文章

热工具

螳螂BT
Mantis是一个易于部署的基于Web的缺陷跟踪工具,用于帮助产品缺陷跟踪。它需要PHP、MySQL和一个Web服务器。请查看我们的演示和托管服务。

VSCode Windows 64位 下载
微软推出的免费、功能强大的一款IDE编辑器

Dreamweaver Mac版
视觉化网页开发工具

SublimeText3 英文版
推荐:为Win版本,支持代码提示!

记事本++7.3.1
好用且免费的代码编辑器