七、排序-算法总结

文章目录

  • 七、排序算法
    • [7.1 常考排序](#7.1 常考排序)
      • [7.1.1 快速排序](#7.1.1 快速排序)
      • [7.1.2 归并排序](#7.1.2 归并排序)
      • [7.1.3 堆排序](#7.1.3 堆排序)

七、排序算法

7.1 常考排序

7.1.1 快速排序

java 复制代码
package com.gyh.reverselinkedlist;

import java.util.*;
import java.util.stream.Collectors;

/**
 * @author Gao YongHao
 * @version 1.0
 */
public class Test1 {
    public static void main(String[] args) {
        int[] nums = {2};
        quickSort(nums, 0, nums.length-1,false);
        Arrays.stream(nums).forEach(System.out::println);

    }

    /**
     * 快排
     * @param nums 原数组
     * @param left 左边界
     * @param right 右边界
     * @param isAsc 是否升序
     */
    private static void quickSort(int[] nums, int left, int right, boolean isAsc){
        if(nums == null || nums.length == 1){
            return;
        }
        int pivot = nums[left]; // 选定第一个数为中轴值
        int l = left , h = right;
        while(l < h){
            while(l<h && (isAsc == (nums[h] >= pivot))){
                h--;
            }
            nums[l] = nums[h];

            while(l<h && (isAsc == (nums[l] <= pivot))){
                l++;
            }
            nums[h] = nums[l];
        }
        nums[l] = pivot; // 摆放中轴值

        // 对左右分别再进行中轴值定位
        if(l - 1>left){
            quickSort(nums, left, l-1, isAsc);
        }
        if(h+1<right){
            quickSort(nums, h+1, right, isAsc);
        }
    }

}

7.1.2 归并排序

java 复制代码
package com.gyh.reverselinkedlist;

import java.util.Arrays;

/**
 * @author Gao YongHao
 * @version 1.0
 */
public class Test2 {
    public static void main(String[] args) {
        int[] nums = {1,22,13,94,5};
        divide(nums, new int[nums.length], 0, nums.length-1,false);
        Arrays.stream(nums).forEach(System.out::println);
    }

    /**
     * 使用分治算法
     * @param nums 数组
     * @param temp 临时数组
     * @param left 保存左边界
     * @param right 保存右边界
     * @param isAsc 是否为升序
     */
    private static void divide(int[] nums, int[] temp, int left, int right, boolean isAsc){
        if(left>=right){
            return;
        }
        int mid = (right+left) / 2;
        divide(nums, temp, left, mid, isAsc);
        divide(nums, temp, mid+1, right, isAsc);
        merge(nums, temp, left, mid+1, right+1, isAsc);
    }

    private static void merge(int[] nums, int[] temp, int l, int r, int end, boolean isAsc){
        int length = 0;
        int start = l;
        int mid = r;
        while(l<mid&&r<end){
            if(isAsc?nums[l]<=nums[r]:nums[r]<=nums[l]){
                temp[length++] = nums[l++];
            }else{
                temp[length++] = nums[r++];
            }
        }
        while(l<mid) temp[length++] = nums[l++];
        while(r<end) temp[length++] = nums[r++];

        length = 0;
        for(int i = start;i<end;i++){
            nums[i] = temp[length++];
        }
    }
}

7.1.3 堆排序

java 复制代码
package com.gyh.reverselinkedlist;

import java.util.Arrays;

/**
 * @author Gao YongHao
 * @version 1.0
 */
public class Test3 {
    public static void main(String[] args) {
        int[] nums = {10,28,1,5,88,17,2,17};
        heapSort(nums, false);
        Arrays.stream(nums).forEach(System.out::println);
    }

    private static void heapSort(int[] nums, boolean isAsc){
        // 对原数组初始化堆
        initHeap(nums, isAsc);
        // 只用作 nums.length-1 次调整堆
        for(int i = nums.length-1;i>0;i--){
            // 将堆顶元素放置于最后
            int temp = nums[0];
            nums[0] = nums[i];
            nums[i] = temp;
            adjustHeap(nums, 0, i-1, isAsc);
        }
    }

    // 初始化堆
    private static void initHeap(int[] nums, boolean isAsc){
        // nums.length/2-1为最后一个非叶子结点的位置
        // 从最后一个非叶子结点依次向上进行堆构建
        for(int i = nums.length/2-1;i>=0;i--){
            adjustHeap(nums, i, nums.length-1,isAsc);
        }
    }

    /**
     * 调整堆
     * @param nums 原数组
     * @param heapTopIndex 堆顶
     * @param lastIndex 最后一个元素的下标
     * @param isAsc 是否升序
     */
    private static void adjustHeap(int[] nums, int heapTopIndex, int lastIndex, boolean isAsc){
        if(heapTopIndex>=lastIndex){
            return;
        }
        // 按完全二叉树结构从最顶至最后一个元素依次进行堆构建
        //
        int heapTopData = nums[heapTopIndex];
        // 首先定位至其左子树
        for(int i = heapTopIndex*2+1;i<=lastIndex;i=i*2+1){
            // 定位满足堆条件的子树
            // 找到子树根节点的最大值对应的下标
            if(i<lastIndex && (isAsc?nums[i+1] > nums[i]:nums[i+1] < nums[i])){
                i++;
            }
            // 找到原始堆顶的最终位置
            if(isAsc?heapTopData >= nums[i]:heapTopData <= nums[i]){
                break;
            }
            // 与子树根节点交换(此处直接覆盖)
            nums[heapTopIndex] = nums[i];
            // 更新栈顶下标
            heapTopIndex = i;
        }
        // 将原始的堆顶元素放置于最终位置
        nums[heapTopIndex] = heapTopData;


    }
}
相关推荐
TiAmo zhang9 分钟前
深度学习与图像处理 | 基于PaddlePaddle的梯度下降算法实现(线性回归投资预测)
图像处理·深度学习·算法
一匹电信狗24 分钟前
【C++】手搓一个STL风格的vector容器
c语言·数据结构·c++·算法·leetcode·stl·visual studio
生信探索29 分钟前
SeuratExtend 可视化教程(1):单细胞分析的高颜值绘图指南
算法
小小小白的编程日记36 分钟前
C语言中的数据结构--栈和队列(2)
c语言·数据结构
李永奉44 分钟前
C语言-数组:数组(定义、初始化、元素的访问、遍历)内存和内存地址、数组的查找算法和排序算法;
c语言·算法·排序算法
星辰大海的精灵1 小时前
深入解析 CopyOnWriteArrayList
java·后端·算法
逝雪Yuki1 小时前
Leetcode——11. 盛最多水的容器
c++·算法·leetcode·双指针
找不到、了1 小时前
Java排序算法之<希尔排序>
java·算法·排序算法
南清的coding日记1 小时前
算法详细讲解- 快速排序与归并排序
数据结构·排序算法
啊阿狸不会拉杆2 小时前
《Java 程序设计》第 8 章 - Java 常用核心类详解
java·开发语言·python·算法·intellij-idea