堆排Java代码实现

堆排复习:

结论:堆排算法时间复杂度为O(nlgn),额外空间复杂度为O(1);

在开始堆排序过程之前先要熟悉两个结构

1,完全二叉树:若设二叉树的深度为h,除第 h 层外,其它各层 (1~h-1) 的结点数都达到最大个数,第 h 层所有的结点都连续集中在最左边,这就是完全二叉树。(摘自百度百科)

大白话:说白了就是建立二叉树的过程中,二叉树每一层都是满节点的,最后一层的节点不许中间有空缺;

2,大根堆:大根堆要求根节点的关键字既大于或等于左子树的关键字值,又大于或等于右子树的关键字值。(摘自百度百科)

大白话:就是在此堆中,任意子树的根节点都是此子树的最大值;

堆排序核心思想:先将无序数组建立大根堆,然后将根节点和二叉树中最后一个节点互换,二叉树Size--,然后重新建立大根堆,然后将根节点和二叉树的最后一个节点互换,然后Size--,如此,一直到二叉树的size=0,此时数组自然已经排好序;

堆排序Java实现如下:

  1 package com.cmbc.test1;
  2
  3 import java.util.Arrays;
  4
  5 public class HeapSortion {
  6
  7
  8     public static void heapSort(int[] arr){
  9         if(arr==null||arr.length<2){
 10             return;
 11         }
 12         //建立大根堆
 13         for(int i = 0;i<arr.length;i++){
 14             heapInsert(arr,i);
 15         }
 16         //建立完大根堆之后,二叉树的size和数组长度是一致的;
 17         int size = arr.length;
 18         swap(arr,0,--size);
 19         while(size>0){
 20             heapify(arr,0,size);
 21             swap(arr,0,--size);
 22         }
 23     }
 24
 25     public static void heapInsert(int[] arr,int index){
 26         while(arr[index]>arr[(index-1)/2]){
 27             swap(arr,index,(index-1)/2);
 28             index = (index-1)/2;
 29         }
 30     }
 31
 32     public static void swap(int[] arr, int i, int j) {
 33         int tmp = arr[i];
 34         arr[i] = arr[j];
 35         arr[j] = tmp;
 36     }
 37
 38
 39     public static void printArray(int[] arr) {
 40         if (arr == null) {
 41             return;
 42         }
 43         for (int i = 0; i < arr.length; i++) {
 44             System.out.print(arr[i] + " ");
 45         }
 46         System.out.println();
 47     }
 48
 49     public static void  heapify(int[] arr,int index,int size){
 50         int left = 2*index+1;
 51         while(left<size){
 52             int largest = left+1<size&&arr[left+1]>arr[left]?left+1:left;
 53             largest = arr[largest]>arr[index]?largest:index;
 54             if(largest==index){
 55                 break;
 56             }
 57             swap(arr,largest,index);
 58             index = largest;
 59             left = largest*2+1;
 60         }
 61     }
 62
 63     public static boolean isEqual(int[] arr1, int[] arr2) {
 64         if ((arr1 == null && arr2 != null) || (arr1 != null && arr2 == null)) {
 65             return false;
 66         }
 67         if (arr1 == null && arr2 == null) {
 68             return true;
 69         }
 70         if (arr1.length != arr2.length) {
 71             return false;
 72         }
 73         for (int i = 0; i < arr1.length; i++) {
 74             if (arr1[i] != arr2[i]) {
 75                 return false;
 76             }
 77         }
 78         return true;
 79     }
 80
 81     public static int[] generateRandomArray(int maxSize, int maxValue) {
 82         int[] arr = new int[(int) ((maxSize + 1) * Math.random())];
 83         for (int i = 0; i < arr.length; i++) {
 84             arr[i] = (int) ((maxValue + 1) * Math.random()) - (int) (maxValue * Math.random());
 85         }
 86         return arr;
 87     }
 88
 89     public static int[] copyArray(int[] arr) {
 90         if (arr == null) {
 91             return null;
 92         }
 93         int[] res = new int[arr.length];
 94         for (int i = 0; i < arr.length; i++) {
 95             res[i] = arr[i];
 96         }
 97         return res;
 98     }
 99
100     public static void main(String[] args) {
101         int testTime = 500000;
102         int maxSize = 100;
103         int maxValue = 100;
104         boolean succeed = true;
105         for (int i = 0; i < testTime; i++) {
106             int[] arr1 = generateRandomArray(maxSize, maxValue);
107             int[] arr2 = copyArray(arr1);
108             heapSort(arr1);
109             Arrays.sort(arr2);
110             if (!isEqual(arr1, arr2)) {
111                 succeed = false;
112                 break;
113             }
114         }
115         System.out.println(succeed ? "正确!" : "请仔细检查");
116
117         int[] arr = generateRandomArray(maxSize, maxValue);
118         printArray(arr);
119         heapSort(arr);
120         printArray(arr);
121     }
122
123 }

原文地址:https://www.cnblogs.com/itqczzz/p/9427826.html

时间: 2024-10-10 02:30:20

堆排Java代码实现的相关文章

java代码实现:12个高矮不同的人,排成两排,每排必须是从矮到高排列,而且第二排比对应的第一排的人高,问排列方式有多少种?

此题参考与其他人思路, 2个解题方式. 1. 1 /** 2 * 用java代码实现:12个高矮不同的人,排成两排,每排必须是从矮到高排列,而且第二排比对应的第一排的人高,问排列方式有多少种? 3 * 状态树方式解 4 * 用状态生成树的方式来做的,先把12个人按从低到高一次编号, 5 * 从(1 ; 2)出发,加入3和4的时候生成(1,3 ; 2,4)和(1,2 ; 3,4), 6 * 然后加入5和6,分别从前面的两个状态出发,可以生成5种状态,就是说6个人时有5种排列 7 * @author

从 Java 代码到 Java 堆

本文将为您提供 Java? 代码内存使用情况的深入见解,包括将 int 值置入一个 Integer 对象的内存开销.对象委托的成本和不同集合类型的内存效率.您将了解到如何确定应用程序中的哪些位置效率低下,以及如何选择正确的集合来改进您的代码. 优化应用程序代码的内存使用并不是一个新主题,但是人们通常并没有很好地理解这个主题.本文将简要介绍 Java 进程的内存使用,随后深入探讨您编写的 Java 代码的内存使用.最后,本文将展示提高代码内存效率的方法,特别强调了 HashMap 和 ArrayL

堆排 归并排序 快排

堆排序的思想 利用大顶堆(小顶堆)堆顶记录的是最大关键字(最小关键字)这一特性,使得每次从无序中选择最大记录(最小记录)变得简单. 其基本思想为(大顶堆): 1)将初始待排序关键字序列(R1,R2....Rn)构建成大顶堆,此堆为初始的无序区: 2)将堆顶元素R[1]与最后一个元素R[n]交换,此时得到新的无序区(R1,R2,......Rn-1)和新的有序区(Rn),且满足R[1,2...n-1]<=R[n]; 3)由于交换后新的堆顶R[1]可能违反堆的性质,因此需要对当前无序区(R1,R2,

JAVA代码实现嵌套层级列表,POI导出嵌套层级列表

要实现POI导出EXCEL形如 --A1(LV1) ----B1(LV2) ----B2(LV2) ------C1(LV3) ------C2(LV3) ----B3(LV2) --A1(LV1) 一.能用到的数据字段 ID(主键).PID(父科目ID).NAME(名称).LEVEL(当前层级) 二.思路: 定义一个空的科目列表用来存放已经排好序的科目.创建一个迭代器传入父节点查出它的所有子节点,遍历子节点插入到科目列表的同时再次调用这个迭代器,这样程序能够在插入一个节点后如果发现有子节点继续

MapReduce实现两表的Join--原理及python和java代码实现

用Hive一句话搞定的,但是有时必须要用mapreduce 方法介绍 1. 概述 在传统数据库(如:MYSQL)中,JOIN操作是非常常见且非常耗时的.而在HADOOP中进行JOIN操作,同样常见且耗时,由于Hadoop的独特设计思想,当进行JOIN操作时,有一些特殊的技巧. 本文首先介绍了Hadoop上通常的JOIN实现方法,然后给出了几种针对不同输入数据集的优化方法. 2. 常见的join方法介绍 假设要进行join的数据分别来自File1和File2. 2.1 reduce side jo

Java 代码性能优化总结

35 个 Java 代码性能优化总结 前言 代码优化,一个很重要的课题.可能有些人觉得没用,一些细小的地方有什么好修改的,改与不改对于代码的运行效率有什么影响呢?这个问题我是这么考虑的,就像大海里面的鲸鱼一样,它吃一条小虾米有用吗?没用,但是,吃的小虾米一多之后,鲸鱼就被喂饱了.代码优化也是一样,如果项目着眼于尽快无BUG上线,那么此时可以抓大放小,代码的细节可以不精打细磨:但是如果有足够的时间开发.维护代码,这时候就必须考虑每个可以优化的细节了,一个一个细小的优化点累积起来,对于代码的运行效率

JAVA代码实现数据结构常用排序算法

下面是用JAVA代码实现的数据结构中的7中基本排序算法: (1)直接插入排序 /** 直接插入排序 **/ /** 数组是引用类型,元素值将被改变 **/ public static void insertSort(int[] table) { /** n-1趟扫描 **/ for (int i = 1; i < table.length; i++) { /** 每趟将table[i]插入到前面已排序的序列中 **/ int temp = table[i], j; /** 将前面较大元素向后移动

STL_算法_Heap算法(堆排)(精)

C++ Primer 学习中... 简单记录下我的学习过程 (代码为主) /***************************************** STL-算法--Heap算法 堆排序算法 (heapsort) make_heap()         //把容器内的数据做堆排序 push_heap()         //向堆内放入元素 pop_heap()          //删除堆顶元素 sort_heap()         //把堆排还原成普通排序 ************

书写性能良好的java代码

书写性能良好的java代码 1.尽量在合适的场合使用单例 使用单例可以减轻加载的负担,缩短加载的时间,提高加载的效率,但并不是所有地方都适用于单例,简单来说,单例主要适用于以下三个方面 第一,控制资源的使用,通过线程同步来控制资源的并发访问 第二,控制实例的产生,以达到节约资源的目的 第三,控制数据共享,在不建立直接关联的条件下,让多个不相关的进程或线程之间实现通信 2.尽量避免随意使用静态变量 要知道,当某个对象被定义为stataic变量所引用,那么gc通常是不会回收这个对象所占有的内存,如