JAVA算法(二)排序算法

这篇具有很好参考价值的文章主要介绍了JAVA算法(二)排序算法。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

一、冒泡排序

定义:相邻的数据两两比较,小的 放前面,大的放后面

过程:

  1. 相邻的元素两两比较,小的放左边,大的放右边。
  2. 第一轮比较完毕之后,最大值就已经确定,第二轮可以少循环一次,后面以此类推。
  3. 如果数组中有n个数据,总共我们只要执行n-1轮的代码就可以。
    private static void bubbleSort(int[] arr) {
    	//确定排序多少次,总长度-1
        for (int i = 0; i < arr.length - 1; i++) {
        	// 每一轮排序,从0开始比较,两两比较;每过一轮,去除末尾数,不进行比较
        	// -1是为了防止索引越界
            for (int j = 0; j < arr.length - 1 - i; j++) {
                if (arr[j] > arr[j+1]) {
                	// 交换位置
                    int temp = arr[j];
                    arr[j] = arr[j+1];
                    arr[j+1] = temp;
                }
            }
        }
        for (int k = 0; k < arr.length; k++) {
            System.err.print(arr[k] + " ");
        }
    }

二、选择排序

定义: 从0索引开始,拿着每一个索引上的元素跟后面的元素依次比较,小的放前面,大的放后面,以此类推。
过程:

  1. 从0索引开始,跟后面的元素一一比较
  2. 小的放前面,大的放后面。
  3. 第一轮循环结束后,最小的数据已经确定
  4. 第二轮循环从1索引开始以此类推。
  5. 第三轮循环从2索引开始以此类推。
    private static void selectSort(int[] arr) {
    	// 外循环,从0开始,跟后面的每个数值比较
        for (int i = 0; i < arr.length-1; i++) {
        	// 内循环,从i后面遍历数据
            for (int j = i+1; j < arr.length; j++) {
                if (arr[i] > arr[j]) {
                    int temp = arr[j];
                    arr[j] = arr[i];
                    arr[i] = temp;
                }
            }
        }

        for (int k = 0; k < arr.length; k++) {
            System.err.print(arr[k] + " ");
        }
    }

三、插入排序

定义:将0索引的元素到N索引的元素看做是有序的,把N+1索引的元素到最后一个当成是无序的。遍历无序的数据,将遍历到的元素插入有序序列中适当的位置,如遇到相同数据,插在后面。

	 private static void insertSort(int[] arr) {
        // 把数组分成两部分,一部分有序,一部分无序
        // int[] arr = {3,5,8,7,1,12,23,9};
        int index = 0;
        for (int i = 0; i < arr.length; i++) {
            if (arr[i] > arr[i+1]) {
                // 获取到无序索引位置
                index = i + 1;
                break;
            }
        }
        System.err.println(index);

        // 外循环, 循环无序部分 7,1,12,23,9
        for (int j = index; j < arr.length; j++) {
            int k = j;
            // 内循环, 循环有序部分 3,5,8
	
			// 方法一
            for (int m = k-1; m >= 0; m--) {
                // 循环一次,索引向前移动一位
                if (arr[m] > arr[k]) {
                    int temp = arr[k];
                    arr[k] = arr[m];
                    arr[m] = temp;
                    k--;
                } else {
                	// 当前面的小于后面的,本轮排序完成,直接跳出循环
                    break;
                }
            }
            
			// 方法二
			while(k >= 1 && arr[k]< arr[k - 1])(//交换位置
				int temp = arr[k];
				arr[k] = arr[k - 1];
				arr[k - 1] = temp;
				k--;
			}

        }
        for (int s = 0; s < arr.length; s++) {
            System.err.print(arr[s] + " ");
        }
    }

四、快速排序

JAVA算法(二)排序算法
JAVA算法(二)排序算法

public static void main(String[] args) {
        int[] arr = {5, 2, 7, 3, 9, 1};
        int[] arrs = quickSort(arr, 0, 5);
        System.err.println(Arrays.toString(arrs));
    }

    /**
     * 快速排序
     *
     * @param arr
     */
    private static void quickSort(int[] arr, int left, int right) {
        if (left < right) {
            int start = left;
            int end = right;
            int key = arr[left];
            while (start < end) {
            	// 右侧结点比key大,下标左移,一直找到比key小的数
                while (arr[end] > key) {
                    end--;
                }
                // 左侧结点比key大,下标右移, 一直找到比key大的数
                while (arr[start] < key) {
                    start++;
                }
                if (arr[start] == arr[end]) {
                    start++;
                } else {
                    int temp = arr[start];
                    arr[start] = arr[end];
                    arr[end] = temp;
                }
            }
            quickSort(arr, left, start - 1);
            quickSort(arr, end + 1, right);
        }
    }

五、希尔排序

JAVA算法(二)排序算法
JAVA算法(二)排序算法

    //希尔排序
    public static void shellSort(int[] arr) {
        //遍历所有的步长
        for (int gap = arr.length / 2; gap > 0; gap = gap / 2) {   // gap = 5
            //遍历所有的元素
            for (int i = gap; i < arr.length; i++) {  // i=5
                //遍历本组中所有元素
                for (int j = i - gap; j >= 0; j -= gap) { //j = 0; j=j-gap
                    //如果当前元素大于 加上步长后的那个元素
                    if (arr[j] > arr[j + gap]) {
                        int temp = arr[j];
                        arr[j] = arr[j + gap];
                        arr[j + gap] = temp;
                    }
                }
            }
            //打印每次排序后的结果
            System.out.println(Arrays.toString(arr));
        }

    }

六、归并排序

归并排序:是建立在归并操作上的一种有效的排序算法。该算法是采用分治法的一个非常典型的应用。

public class MergeSort {

    /**
     * 归并排序
     *
     * @param array 待排序的数组
     */
    public static void mergeSort(int[] array) {
        if (array == null || array.length < 2) {
            return;
        }

        // 进行归并排序
        sort(array, 0, array.length - 1);
    }

    /**
     * 对数组进行归并排序
     *
     * @param array 待排序的数组
     * @param left  排序的左边界
     * @param right 排序的右边界
     */
    public static void sort(int[] array, int left, int right) {
        if (left >= right) {
            return;
        }
        int mid = (right +left) / 2 // 计算中间位置
        sort(array, left, mid); // 对左半部分进行归并排序
        sort(array, mid + 1, right); // 对右半部分进行归并排序
        merge(array, left, mid, right); // 合并左右两个有序数组
    }

    /**
     * 合并左右两个有序数组
     *
     * @param array 待合并的数组
     * @param left  左半部分的左边界
     * @param mid   中间位置
     * @param right 右半部分的右边界
     */
    public static void merge(int[] array, int left, int mid, int right) {
        int[] tmp = new int[right - left + 1]; // 临时数组
        int i = left, j = mid + 1, k = 0;
        while (i <= mid && j <= right) { // 依次比较左右两个数组的元素
            if (array[i] <= array[j]) {
                tmp[k++] = array[i++];
            } else {
                tmp[k++] = array[j++];
            }
        }
        while (i <= mid) { // 将左边数组中剩余的元素放入临时数组
            tmp[k++] = array[i++];
        }
        while (j <= right) { // 将右边数组中剩余的元素放入临时数组
            tmp[k++] = array[j++];
        }
        for (int l = 0; l < tmp.length; l++) { // 将临时数组中的元素复制回原数组
            array[left + l] = tmp[l];
        }
    }
}

七、堆排序

大顶堆:每个节点的值都大于或等于其子节点的值,在堆排序算法中用于升序排列;
小顶堆:每个节点的值都小于或等于其子节点的值,在堆排序算法中用于降序排列;

public static void heapSort(int[] arr) {
        // 获取数组长度
        int length = arr.length;
        // 获取最后一个非叶子节点下标 : length / 2 - 1
        for (int i = length / 2 - 1; i >= 0; i--) {
            // 把数组转化为堆,我们称之为建堆
            buildHeap(arr, i, length);
        }
        System.err.println("数组建堆后的结果:{}"+ Arrays.toString(arr));
        // 排序,因为之前已经完成了建堆,意味着,根节点就是我们需要的值
        for (int k = length - 1; k >= 0; k--) {
            // 将当前根节点与未排序的最大子节点进行交换
            swap(arr, 0, k);
            // 剩下的元素继续建堆,要理解i--,刚刚交换的根节点的值就是已排序的不会参与遍历了
            buildHeap(arr, 0, k);
        }
    }

    private static void buildHeap(int[] arr, int i, int length) {
        // 大顶堆的节点调整
        while (true) {
            // 定义最大节点的位置---父节点
            int maxPos = i;
            // 检查在未排序列表中,当前节点的值是不是小于它的左子节点(2i+1)---左节点
            if (i * 2 + 1 < length && arr[i] < arr[i * 2 + 1]) {
                maxPos = i * 2 + 1;
            }
            // 检查在未排序列表中,同时当前的最大节点和i节点的右子节点(2i+2)也比较找出最大值的节点---右节点
            // 也就是找出父节点,左节点,右节点三者中的最大节点值
            if (i * 2 + 2 < length && arr[maxPos] < arr[i * 2 + 2]) {
                maxPos = i * 2 + 2;
            }
            // maxPos没变说明已经找不到比当前节点大的了
            if (maxPos == i) {
                break;
            }
            // 交换两个节点(当前节点和最大值的节点进行交换)
            swap(arr, i, maxPos);
            // 继续往下处理这个过程()处理调整后,下面的子节点情况
            i = maxPos;
        }
        System.err.println("大顶堆的节点调整后结果:{}"+ Arrays.toString(arr));
    }

    private static void swap(int[] arr, int i, int j) {
        int temp = arr[i];
        arr[i] = arr[j];
        arr[j] = temp;
    }

    public static void main(String[] args) {
        int[] arr = new int[]{28, 8, 10, 23, 21, 19, 9};
        System.err.println("要排序的初始化数据:{}"+ Arrays.toString(arr));
        //从小到大排序
        heapSort(arr);
    }

八、计数排序

计数排序是一个排序时不比较大小的排序算法。对于数组里的每个元素来说,如果能知道数组里有多少项小于或等于该元素,就能准确地给出该元素在排序后的数组位置。
数组里所有元素都是正整数。

public static void main(String[] args) {
        int[] arr = {1003,1005,1004,1000,1003,1004,1000,1004};

        countSort(arr);
    }

    private static void countSort(int[] arr) {
        int max = arr[0];
        int min = arr[0];
        for (int i = 0; i < arr.length; i++) {
            if (arr[i] > max) {
                max = arr[i];
            }
            if (arr[i] < min) {
                min = arr[i];
            }
        }
        int[] numberArr = new int[max - min + 1];

        for (int j = 0; j < arr.length; j++) {
            int num = arr[j] - min;
            numberArr[num]++;
        }

        int index = 0;
        for (int k = 0; k < numberArr.length; k++) {
            for (int n = 0; n<numberArr[k];n++){
                arr[index] = k + min;
                index++;
            }
        }
        System.err.println(Arrays.toString(arr));

    }

九、桶排序

桶排序(Bucket sort)是计数排序算法的升级版,将数据分到有限数量的桶子里,然后每个桶再分别排序

 public static void main(String[] args) {
        int[] arr = {15,8,23,38,28,19,32,21,9};

        bucketSort(arr, 4);

    }

    private static void bucketSort(int[] arr, int size) {
        int max = Integer.MIN_VALUE;
        int min = Integer.MAX_VALUE;

        for (int i = 1; i < arr.length; i++) {
            max = Math.max(max, arr[i]);
            min = Math.min(min, arr[i]);
        }

        //桶编号 =(数组元素 - 最小值) (桶个 - 1) /(最大值 - 最小值)
		// 先查询出二维数组第二列的长度,也就是每个桶放了多少
        int[] bucketSize = new int[size];
        for (int i = 0; i < arr.length; i++) {
            int code = (arr[i] - min) * (size - 1) /(max - min);
            bucketSize[code]++;
        }
		// 定义二维数组
        int[][] bucket = new int[size][];
        for (int code = 0; code < size; code++) {
            bucket[code] = new int[bucketSize[code]];
        }
		// 向二维数组赋值
        int[] bucketSize2 = new int[size];
        for (int number : arr) {
            int code = (number - min) * (size - 1) / (max - min);
            bucket[code][bucketSize2[code]] = number;
            bucketSize2[code]++;
        }
		// 每个桶冒泡排序
        for (int n = 0; n < bucket.length; n++) {
            int[] midArr = bubbleSort(bucket[n]);
            bucket[n] = midArr;
        }

        // 遍历桶,得到排序后结果
        int index = 0;
        int[] sortArr = new int[arr.length];
        for (int t = 0; t < bucket.length; t++) {
            for (int m = 0; m < bucketSize[t]; m++) {
                sortArr[index] = bucket[t][m];
                index++;
            }
        }

        for (int i : sortArr) {
            System.err.print(i + " ");
        }


    }

    private static int[] bubbleSort(int[] arr) {
        //确定排序多少次,总长度-1
        for (int i = 0; i < arr.length - 1; i++) {
            // 每一轮排序,从0开始比较,两两比较;每过一轮,去除末尾数,不进行比较
            // -1是为了防止索引越界
            for (int j = 0; j < arr.length - 1 - i; j++) {
                if (arr[j] > arr[j+1]) {
                    // 交换位置
                    int temp = arr[j];
                    arr[j] = arr[j+1];
                    arr[j+1] = temp;
                }
            }
        }
        return arr;
    }
    public static void bucketsort(int[] arr, int bucketSize) {
        // 初始化最大最小值
        int max = Integer.MIN_VALUE;
        int min = Integer.MAX_VALUE;
        // 找出最小值和最大值
        for (int num : arr) {
            max = Math.max(max, num);
            min = Math.min(min, num);
        }

        // 创建bucketSize个桶
        List<List<Integer>> bucketList = new ArrayList<>();
        for (int i = 0; i < bucketSize; i++) {
            bucketList.add(new ArrayList<>());
        }
        // 将数据放入桶中
        for (int num : arr) {
            // 确定元素存放的桶号  //重点
            int bucketIndex = (num - min) * (bucketSize - 1) / (max - min);
            List<Integer> list = bucketList.get(bucketIndex);
            list.add(num);
        }
        // 遍历每一个桶
        int arrIndex = 0;
        for (int i = 0; i < bucketList.size(); i++) {
            List<Integer> list = bucketList.get(i);
            list.sort(null);
            // 对每一个桶排序
            for (int value : list) {
                arr[arrIndex++] = value;
            }
        }
        for (int i : arr) {
            System.err.print(i + " ");
        }
    }

十、基数排序

基数排序不支持负数,想要使用,需要整体增加最小值的绝对值,变成正数,排序后,再减文章来源地址https://www.toymoban.com/news/detail-448329.html

public static void main(String[] args) {
        int[] arr = {53, 3, 542, 0, 748, 14, 214};
        radixSort(arr);
    }

    private static void radixSort(int[] arr) {
        int max = arr[0];
        for (int k = 0; k < arr.length; k++) {
            if (arr[k] > max) {
                max = arr[k];
            }
        }
        int maxLength = (max + "").length();
        for (int t = 0; t < maxLength; t++) {
            int[][] bucket = new int[10][arr.length];
            int[] wsBucket = new int[10];

            int divide = (int) Math.pow(10, t);
            for (int i = 0; i < arr.length; i++) {
                int ws = arr[i] / divide % 10;
                bucket[ws][wsBucket[ws]] = arr[i];
                wsBucket[ws]++;
            }

            int index = 0;
            for (int m = 0; m < wsBucket.length; m++) {
                if (wsBucket[m] != 0) {
                    for (int k = 0; k < wsBucket[m]; k++) {
                        arr[index] = bucket[m][k];
                        index++;
                    }
                }
            }
            System.err.println(Arrays.toString(arr));
        }

    }

到了这里,关于JAVA算法(二)排序算法的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • 【数据结构与算法】十大经典排序算法-冒泡排序

    🌟 个人博客: www.hellocode.top 🏰 Java知识导航: Java-Navigate 🔥 CSDN: HelloCode. 🌴 掘金 :HelloCode 🌞 知乎 :HelloCode ⚡如有问题,欢迎指正,一起学习~~ 冒泡排序(Bubble Sort)是一种简单的排序算法,它通过重复地交换相邻元素的位置来将最大(或最小)的元素逐步“冒泡”到

    2024年02月14日
    浏览(75)
  • 【数据结构与算法】排序算法(选择排序,冒泡排序,插入排序,希尔排序)

    基本概念这了就不浪费时间解释了,这四种都是很简单的排序方式,本专栏后续文章会出归并排序,计数排序,快速排序,堆排序,桶排序等排序算法,今天这篇文章中给出选择排序,冒泡排序,插入排序和希尔排序的实现; 如果发现文章中有错误,还请大家指出来,我会非

    2024年02月15日
    浏览(86)
  • 数据结构算法练习 插入排序 冒泡排序

    插入排序 代码如下  package main import \\\"fmt\\\" func main() {     a := []int{4, 5, 6, 1, 3, 2}         b := insert(a)     for i := 0; i len(b); i++ {         fmt.Println(b[i])     } } func insert(a []int) []int {     if len(a) = 1 {                   如果数组长度小于等于1 不用排序直接返回          retur

    2024年02月08日
    浏览(58)
  • 数据结构算法--2 冒泡排序,选择排序,插入排序

    思想就是将相邻元素两两比较,当一个元素大于右侧相邻元素时,交换他们的位置,小于右侧元素时,位置不变,最终序列中的最大元素,像气泡一样,到了最右侧。 这时冒泡排序第一轮结束,数列最右侧元素9的位置可认为是一个有序区,有序区目前有一个元素. 第二轮排序

    2024年02月13日
    浏览(64)
  • (java版)排序算法----【冒泡,选择,插入,希尔,快速排序,归并排序,基数排序,堆排序】超详细~~

    目录 冒泡排序(BubbleSort): 代码详解:  冒泡排序的优化:  选择排序(SelectSort): 代码详解:  插入排序(InsertSort): 代码详解:  希尔排序(ShellSort):  法一(交换法)代码详解:  法二(移位法--插入排序的优化)代码详解: 快速排序(QuickSort):  代码详解:  归并排

    2024年02月20日
    浏览(48)
  • 【数据结构】排序算法(二)—>冒泡排序、快速排序、归并排序、计数排序

    👀 樊梓慕: 个人主页  🎥 个人专栏: 《C语言》《数据结构》《蓝桥杯试题》《LeetCode刷题笔记》《实训项目》 🌝 每一个不曾起舞的日子,都是对生命的辜负 目录 前言 1.冒泡排序 2.快速排序 2.1Hoare版 2.2占坑版 2.3前后指针版 2.4三数取中对快速排序的优化 2.5非递归版 3.归

    2024年02月08日
    浏览(54)
  • 七大排序算法——冒泡排序,通俗易懂的思路讲解与图解(完整Java代码)

    排序:所谓排序,就是使一串记录,按照其中的某个或某些的大小,递增或递减的排列起来的操作。 上述待排序的数中,有两个5。 将 前面 的5标记一个a, 将 后面 的5标记一个b。 通过算法进行排序后,这一组数就有序了, 但是要看两个相同的5的位置是否有改变。

    2024年02月16日
    浏览(39)
  • 【数据结构与算法】冒泡排序算法(BubbleSort)

    目录 1、缘起 2、BubbleSort 算法描述 3、用图示描述 BubbleSort 算法 4、C 语言描述 5、Python 语言描述  6、Java 语言描述  7、总结         冒泡排序算法 是一个非常经典的算法,它是各大网络编程平台上的座上宾,面试官口中的最爱。这个算法就是因其中数字从列表的开始向顶

    2024年02月03日
    浏览(43)
  • [ 数据结构 -- 手撕排序算法第二篇 ] 冒泡排序

    手撕排序算法系列之:冒泡排序。 从本篇文章开始,我会介绍并分析常见的几种排序,大致包括 插入排序 , 冒泡排序 ,希尔排序,选择排序,堆排序,快速排序,归并排序等。 大家可以点击此链接阅读其他排序算法:排序算法_大合集(data-structure_Sort) 本篇主要来手撕冒

    2024年02月11日
    浏览(59)
  • 直接插入排序、希尔排序、直接选择排序、堆排序、冒泡排序——“数据结构与算法”

    各位CSDN的uu们你们好呀,今天小雅兰的内容是数据结构与算法啦,是排序!!!下面,让我们进入七大排序的世界吧!!! 排序:所谓排序,就是使一串记录,按照其中的某个或某些的大小,递增或递减的排列起来的操作。 稳定性:假定在待排序的记录序列中,存在

    2024年02月15日
    浏览(70)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包