热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

java分治排序算法_Java学习笔记——排序算法之进阶排序(堆排序与分治并归排序)...

春蚕到死丝方尽,蜡炬成灰泪始干——无题这里介绍两个比较难的算法:1、堆排序2、分治并归排序先说堆。这里请大家先自行了解完全二叉树的数据结构。堆是完全二叉

春蚕到死丝方尽,蜡炬成灰泪始干

——无题

这里介绍两个比较难的算法:

1、堆排序

2、分治并归排序

先说堆。

这里请大家先自行了解完全二叉树的数据结构。

堆是完全二叉树。大顶堆是在堆中,任意双亲值都大于(或等于)其孩子值,就称其为大顶堆。

堆排序的步骤:

1、把数组想象成一个堆。数组的index+1就是其对应在堆中的序号

2、调堆中各值的顺序,得到大顶堆

3、将堆首位值与堆末尾值交换,最大值排序完毕

4、将堆得大小减1,重复步骤2和步骤3,直到堆中只剩下一个元素。排序完毕

上代码:

1 public classHeapSort {2

3 public static void heapSort(int[] arr){4 //建立完全二叉树,从最后一个双亲开始调整双亲值,直到根,调整完毕后大顶堆建立完成

5 for (int i = arr.length >> 1; i > 0; i --) {6 heapAdjust(arr, i, arr.length);//调用堆要从1到length才符合堆的定义

7 }8 //堆顶和堆低交换,获取最大值,然后调整大顶堆

9 for (int i = arr.length - 1; i > 0; i--) {10 arr[i] = arr[i]^arr[0];11 arr[0] = arr[i]^arr[0];12 arr[i] = arr[i]^arr[0];13 heapAdjust(arr, 1, i);//因为堆计数要从1开始,所以size = endIndex + 1

14 }15 }16 //调整大顶堆.先找左子,然后和右子比,取值大的,在和双亲自己比,自己比儿子大,break,否则交换.注意:根要从1开始才能找到左子

17 public static void heapAdjust(int[] arr, int parents, intsize){18 int j;//孩子们的标记是j,索引全部-1

19 int i = parents;//双亲是i,索引全部-1

20 while (i <<1 <&#61;size) {21 j &#61; i <<1;//左子

22 if (j &#43; 1 <&#61; size) {//有右子

23 if (arr[j - 1] arr[j - 1])27 break;28 arr[i-1] &#61; arr[i-1]^arr[j-1];29 arr[j-1] &#61; arr[i-1]^arr[j-1];30 arr[i-1] &#61; arr[i-1]^arr[j-1];31 i &#61; j;//儿子变为父亲,这里不知道是左子还是右子,所以不能直接通过for循环的迭代步骤<

32 }33 }34 }

再说分治并归排序

这里先要了解什么是递归

1 public classMergingTest {2

3 public static voidmain(String[] args) {4 mSort(0, 3);5 }6 private static void mSort(int left, intright) {7 int m &#61; (left &#43; right)/2;8 if (left &#61;&#61;right) {9 System.out.println(left);10 return;11 }12 mSort(left, m);13 mSort(m&#43;1, right);14 }15 }

这几行代码是并归算法的核心。运行代码将输出0123456789&#xff0c;虽然看上去很简单&#xff0c;但是如果真能明白&#xff0c;说明你已经完全理解递归的思想了&#xff0c;写出并归算法也就不在话下了。

为什么会输出0123呢&#xff1f;

f266f67bca4e91d0d8d534b812785802.png

代码执行的走向&#xff1a;1→2→4→2→5→2→1→3→6→3→7→3→1→return

能领悟这个东西就好办了&#xff0c;上代码:

1 public classMergingSort {2

3 public static void mergingSort(int[] arr) {4 int[] temp &#61; new int[arr.length];

//temp是相当于一张牌&#xff0c;通过left,m,right在逻辑上分成两个数组&#xff0c;进行分治排序,arr是原数组&#xff0c;对数组排序不传数组怎么行&#xff1f;&#xff01;5 mSort(arr, temp, 0, arr.length-1);6 }7 private static void mSort(int[] arr, int[] temp, int left, intright) {

//这里的分组逻辑没有使用到temp和arr&#xff0c;而是把它们作为参数传入merge方法8 int m &#61; (left&#43;right)/ 2;9 if (left &#61;&#61;right) {10 return;11 }12 mSort(arr, temp, left, m);13 mSort(arr, temp, m&#43;1, right);14 merge(arr,temp,left,m,right);15 }16 private static void merge(int[]arr, int[] temp, int left, int m, intright) {

//分治排序极其简单&#xff0c;已知两个有序数组&#xff0c;要把他们合并成一个有序数组&#xff0c;用什么方法都不用说&#xff0c;大家一想就知道了。17 for (int c &#61; 0;c

//使用分支结构&#xff0c;把每摞牌最小的那个挑出来给arr27 if (temp[i]

//使用分支结构&#xff0c;把剩下的那摞牌都塞给arr34 if (i >m) {35 while (j <&#61;right) {36 arr[k&#43;&#43;] &#61; temp[j&#43;&#43;];37 }38 }39 if (j >right) {40 while (i <&#61;m) {41 arr[k&#43;&#43;] &#61; temp[i&#43;&#43;];42 }43 }44 }45

46 }



推荐阅读
  • 动态规划算法的基本步骤及最长递增子序列问题详解
    本文详细介绍了动态规划算法的基本步骤,包括划分阶段、选择状态、决策和状态转移方程,并以最长递增子序列问题为例进行了详细解析。动态规划算法的有效性依赖于问题本身所具有的最优子结构性质和子问题重叠性质。通过将子问题的解保存在一个表中,在以后尽可能多地利用这些子问题的解,从而提高算法的效率。 ... [详细]
  • [大整数乘法] java代码实现
    本文介绍了使用java代码实现大整数乘法的过程,同时也涉及到大整数加法和大整数减法的计算方法。通过分治算法来提高计算效率,并对算法的时间复杂度进行了研究。详细代码实现请参考文章链接。 ... [详细]
  • Iamtryingtomakeaclassthatwillreadatextfileofnamesintoanarray,thenreturnthatarra ... [详细]
  • 本文介绍了使用Java实现大数乘法的分治算法,包括输入数据的处理、普通大数乘法的结果和Karatsuba大数乘法的结果。通过改变long类型可以适应不同范围的大数乘法计算。 ... [详细]
  • Java容器中的compareto方法排序原理解析
    本文从源码解析Java容器中的compareto方法的排序原理,讲解了在使用数组存储数据时的限制以及存储效率的问题。同时提到了Redis的五大数据结构和list、set等知识点,回忆了作者大学时代的Java学习经历。文章以作者做的思维导图作为目录,展示了整个讲解过程。 ... [详细]
  • 本文介绍了如何在给定的有序字符序列中插入新字符,并保持序列的有序性。通过示例代码演示了插入过程,以及插入后的字符序列。 ... [详细]
  • 本文详细介绍了Java中vector的使用方法和相关知识,包括vector类的功能、构造方法和使用注意事项。通过使用vector类,可以方便地实现动态数组的功能,并且可以随意插入不同类型的对象,进行查找、插入和删除操作。这篇文章对于需要频繁进行查找、插入和删除操作的情况下,使用vector类是一个很好的选择。 ... [详细]
  • 猜字母游戏
    猜字母游戏猜字母游戏——设计数据结构猜字母游戏——设计程序结构猜字母游戏——实现字母生成方法猜字母游戏——实现字母检测方法猜字母游戏——实现主方法1猜字母游戏——设计数据结构1.1 ... [详细]
  • 多维数组的使用
    本文介绍了多维数组的概念和使用方法,以及二维数组的特点和操作方式。同时还介绍了如何获取数组的长度。 ... [详细]
  • Go语言实现堆排序的详细教程
    本文主要介绍了Go语言实现堆排序的详细教程,包括大根堆的定义和完全二叉树的概念。通过图解和算法描述,详细介绍了堆排序的实现过程。堆排序是一种效率很高的排序算法,时间复杂度为O(nlgn)。阅读本文大约需要15分钟。 ... [详细]
  • Parity game(poj1733)题解及思路分析
    本文是对题目"Parity game(poj1733)"的解题思路进行分析。题目要求判断每次给出的区间内1的个数是否和之前的询问相冲突,如果冲突则结束。本文首先介绍了离线算法的思路,然后详细解释了带权并查集的基本操作。同时,本文还对异或运算进行了学习,并给出了具体的操作步骤。最后,本文给出了完整的代码实现,并进行了测试。 ... [详细]
  • 颜色迁移(reinhard VS welsh)
    不要谈什么天分,运气,你需要的是一个截稿日,以及一个不交稿就能打爆你狗头的人,然后你就会被自己的才华吓到。------ ... [详细]
  • 欧拉回路是指不令笔离开纸面,可画过图中每条边仅一次,且可以回到起点的一条回路。现给定一个图,问是否存在欧拉回路?Input测 ... [详细]
  • 那你就是学的c语言,跟我学c语言
    本文目录一览:1、如何学习C语言?2、新手如何 ... [详细]
  • 分支结构程序设计练习
    任务1:从键盘输入三个整数,按从小到大排序输出。实现思路:定义三个整形变量x,y,z,分别存放从键盘输入的整数。比较x和y的值,如果xy,则x和y的值交换;比较x和z的值, ... [详细]
author-avatar
小天
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有