zoukankan      html  css  js  c++  java
  • java实现桶排序

    桶排序是指:将待排序数组中的元素划分为多个桶(范围段),对每个桶分别进行排序,将多个桶组合即为排序结果。

    桶排序的时间复杂度为O(n + c),  其中n为待排序数据量,c = n * (logn - logm), m为桶的个数。极端情况下,当桶的个数与数据量相等时,桶排序时间复杂度为O(n)。

    看一些博客里写道桶排序是稳定排序,另一些博客则说是非稳定排序。实际上,桶排序的稳定性取决于桶内排序所使用的算法,若使用插入排序,则是稳定排序,若使用快排,则是非稳定排序。

     1 import java.util.Arrays;
     2 
     3 public class BucketSort {
     4     public static void main(String[] args) {
     5         int[] array = {9, 8, 7, 6, 5, 4, 3, 2, 1, 0};
     6         bucketSort(array);
     7         System.out.println(Arrays.toString(array));
     8     }
     9 
    10     public static void bucketSort(int[] arr) {
    11         if (arr == null || arr.length == 0) {
    12             return;
    13         }
    14         int len = arr.length;
    15         // 根据原始序列的长度,设置桶的数量。这里假设每个桶放最多放4个元素
    16         int bucketCount = len / 4;
    17         // 遍历原始序列,找出最大值和最小值
    18         int min = 0, max = 0;
    19         for (int i = 0; i < len; i++) {
    20             if (arr[i] > max) {
    21                 max = arr[i];
    22             } else if (arr[i] < min) {
    23                 min = arr[i];
    24             }
    25         }
    26         // 每个桶的数值范围
    27         int range = (max - min + 1) / bucketCount;
    28         int[][] buckets = new int[bucketCount][];
    29         // 遍历原始序列
    30         for (int i = 0; i < len; i++) {
    31             int val = arr[i];
    32             // 计算当前值属于哪个桶
    33             int bucketIndex = (int) Math.floor((val - min) / range);
    34             // 向桶中添加元素
    35             buckets[bucketIndex] = appendItem(buckets[bucketIndex], val);
    36         }
    37         // 最后合并所有的桶
    38         int k = 0;
    39         for (int[] b : buckets) {
    40             if (b != null) {
    41                 for (int i = 0; i < b.length; i++) {
    42                     arr[k++] = b[i];
    43                 }
    44             }
    45         }
    46     }
    47 
    48     private static int[] appendItem(int[] bucketArr, int val) {
    49         if (bucketArr == null || bucketArr.length == 0) {
    50             return new int[]{val};
    51         }
    52         // 拷贝一下原来桶的序列,并增加一位
    53         int[] arr = Arrays.copyOf(bucketArr, bucketArr.length + 1);
    54         // 这里使用插入排序,将新的值val插入到序列中
    55         int i;
    56         for (i = arr.length - 2; i >= 0 && arr[i] > val; i--) {
    57             // 从新序列arr的倒数第二位开始向前遍历(倒数第一位是新增加的空位,还没有值)
    58             // 如果当前序列值大于val,那么向后移位
    59             arr[i + 1] = arr[i];
    60         }
    61         arr[i + 1] = val;
    62         return arr;
    63     }
    64 }
  • 相关阅读:
    c# 发送邮件
    C# Android 开发中使用 Sqlite.NET ORM
    VS2015 使用 Visual Studio Emulator For Android 调试无法命中断点的解决办法?
    asp.net 下载文件
    ScriptManager 发送错误到客户端
    C# 比较两个路径是否指向同一对象
    IIS 集成模式 导致 AjaxPro 无法正常运行
    C#编码、解码与ASP.NET编码解码对应函数
    FTP 命令连接(带用户名和密码)方法
    医学-药物-大环内酯类-阿奇霉素(Azithromycin)
  • 原文地址:https://www.cnblogs.com/javaXRG/p/11604307.html
Copyright © 2011-2022 走看看