深入浅出排序算法之计数排序

news2024/9/23 17:11:01

目录

1. 原理

2. 代码实现

3. 性能分析


1. 原理

首先看一个题目,有n个数,取值范围是 0~n,写出一个排序算法,要求时间复杂度和空间复杂度都是O(n)的。

为了达到这种效果,这一篇将会介绍一种不基于比较的排序方法。这种方法被称为计数排序。

计数排序的思路是这样的,对于每一个待排序元素a,如果知道了待排序数组中有多少个比它小的数,那么就可以直接知道在排序后的数组中 a 应该在什么位置上。比如,如果一个数组中有3个数是比a小的,那么,在排序后的数组里,a必然会出现在第4位。

现在问题转化成,对于待排序数组里的一个数,如何能快速知道比它小的数字有多少个。要解决这个问题,我们不能使用比较的办法,那样时间复杂度是无法降下来,只有换一个思路,以空间换时间。因为n个数的取值范围是 0~n,所以,不妨使用一个大小为 n 的数组来统计从0到n,每个数在待排序数组中出现的次数。这个数组类似于直方图数组,因为这种方式也被称做是基于统计的排序。直方图统计的思路简单清晰,在很多题目中都会有出现,一定要熟练掌握这种技巧。

强调:计数排序适合排序一组集中的数据。

2. 代码实现

    //计数排序
    public static void countSort(int[] array) {
        //1. 找到待排序数组的范围,也就是找到最大值和最小值
        int max = array[0];
        int min = array[0];
        //循环遍历找寻最小值和最大值
        for (int i = 1; i < array.length; i++) {
            if (array[i] > max)
                max = array[i];
            if (array[i] < min)
                min = array[i];
        }
        //计算待排数组的长度
        int len = max - min + 1;
        //2. 定义一个计数数组
        int[] count = new int[len];
        //3. 遍历array数组,把数据计数到计数数组中
        for (int i = 0; i < array.length; i++) {
            count[array[i] - min]++;
        }
        //4. 将array数组还原
        int index = 0;//来控制array数组的下标
        for (int i = 0; i < array.length; i++) {
            //这个循环的作用,是把count里面标记的数据取出来
            while (count[i] > 0) {
                array[index] = i + min;
                index++;
                count[i]--;
            }
        }
    }

        public static void main(String[] args) {
        int[] a = {5,4,3,2,1};
        Sort.countSort(a);
        for (int x : a) {
            System.out.print(x + " ");
        }
    }

3. 性能分析

时间复杂度空间复杂度
O(MAN(N,范围))O(N)
对数据的范围敏感对数据的范围敏感

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1143684.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Day 11 python学习笔记

模块 内置模块 random random&#xff1a;随机数模块 我们可以在解释器中看到其蕴含的方法 接下来我解释一些常用的方法&#xff1a; random.random( ) random.random( ) 返回0-1的随机数 [0,1) >>> random.random() 0.364183511476754 random.randint(n,m) r…

Java JSON字符串转换成JSON对象

方法一&#xff1a;要先转为LinkedHashMap&#xff0c;再转json&#xff08;推荐&#xff0c;我使用这种方法&#xff09; String jsonStr"{\"id\":\"10001\",\"name\":\"肉类\",\"menus\":[{\"name\":\&qu…

Node切换版本

以非安转版本方式安装Node&#xff0c;经常会需要进行Node的版本切换。 官方的做法是&#xff1a;nvm use version。 但是这种方法经常会失败。如下&#xff1a; 其实nvm命令的本质就是给当前node版本添加一个快捷方式&#xff08;或软连接&#xff09;&#xff0c;因为环境变…

AT800(3000) +昇腾300V 之一 环境部署

环境部署 背景服务器 硬件资源系统&#xff1a;CPU&#xff1a;NPU&#xff1a;固件与驱动CANN 背景 因nvidia 受限 公司转华为推理服务器 AT800&#xff08;3000&#xff09; 昇腾 &#xff0c;将推出一系列文章 &#xff0c;记录过程。 服务器 硬件资源 系统&#xff1a;…

再畅通工程(最小生成树)

题目描述&#xff1a;还是畅通工程 某省调查乡村交通状况&#xff0c;得到的统计表中列出了任意两村庄间的距离。省政府“畅通工程”的目标是使全省任何两个村庄间都可以实现公路交通&#xff08;但不一定有直接的公路相连&#xff0c;只要能间接通过公路可达即可&#xff09;&…

轻量封装WebGPU渲染系统示例<6>-混合模式(源码)

当前示例源码github地址: https://github.com/vilyLei/voxwebgpu/blob/version-1.01/src/voxgpu/sample/BlendTest.ts 此示例渲染系统实现的特性: 1. 用户态与系统态隔离。 2. 高频调用与低频调用隔离。 3. 面向用户的易用性封装。 4. 渲染数据和渲染机制分离。 5. 用户…

8086汇编环境的使用

先打开emu8086&#xff0c;写入代码 ;给11003H的地址赋1234H的值;不能直接给DS赋值需要寄存器中转 mov dx, 1100H mov ds, dx mov ax, 1234H ;不能直接给内存地址赋值&#xff0c;需要DS:[偏移地址]指向内存 mov [3H], ax 点击emulate开始模拟 出现调试框&#xff0c;调试框的…

moviepy处理手机端图片旋转问题

1.手机拍摄的图片或者在ffmpeg处理的时候&#xff0c;会读取图片的元数据从而进行旋转 左边是拍摄的图片&#xff0c;右侧是进行处理以后得图片 video VideoFileClip(file_path) if video.rotation in (90, 270):video video.resize(video.size[::-1])video.rotation 0

Live800:智能客服的意义和价值

近年来&#xff0c;智能客服系统的出现引起了各行各业的共同关注&#xff0c;成为了许多企业在数字化转型中的重要步骤之一。智能客服系统能够帮助企业降低人力成本&#xff0c;提高客户满意度&#xff0c;对于企业而言具有不可替代的价值和意义。 智能客服系统的主要价值包括以…

Diffusion Models视频生成-博客汇总

0、【论文汇总】Diffusion Models视频生成/视频编辑/可控视频生成/跨模态视频生成 本文总结了Diffusion Models视频生成领域相关的工作,目前共收录142篇,持续更新中。 1、Video Diffusion Models:基于扩散模型的视频生成 扩散模型已经被广泛运用到图像生成、image-to-image转…

网络搭建和运维的基础题目

服务部分&#xff08;linux&#xff09; 实操部分 1.在任意文件夹下面创建形如 A/B/C/D 格式的文件夹系列。 [rootlocalhost ~]# mkdir -p A/B/C/D 2.在创建好的文件夹下面&#xff0c;A/B/C/D &#xff0c;里面创建文本文件 mkdir.txt [rootlocalhost ~]# cd A/B/C/D [r…

前端跨页面通信,你知道哪些方法?

一、同源页面 1.广播站模式 一个页面将消息通知给一个“中央站”&#xff0c;再由“中央站”通知给各个页面&#xff0c;以下会介绍这个中央站可以是LocalStorage&#xff0c;可以是BroadCast Channel实例&#xff0c;也可以是一个Service worker 1.1.LocalStorageStorageEven…

[AUTOSAR][诊断管理][ECU][$27] 安全访问

文章目录 一、简介$27服务有何作用,为什么要有27服务呢?功能描述应用场景安全解锁基本原理服务请求服务响应Verify Key负响应NRC支持二、常见Bug大揭秘三、示例代码uds27_security_access.c一、简介 $27服务有何作用,为什么要有27服务呢? 功能描述 根据ISO14119-1标准中…

网络基础-3

路由开销 一条路由的开销时指到达这条路由的目的地/掩码需要付出的带价值。同一种路由协议发现有多条路由可以到达同一目的地/掩码时&#xff0c;将优选开销最小的路由&#xff0c;即只把开销最小的路由加入进本协议的路由表中。 路由协议 内部网关协议&#xff08;IGP&…

【C++项目】高并发内存池第六讲 当申请内存大于256K时的处理

目录 1.申请过程2.释放过程 1.申请过程 当申请的内存大于256kb时直接向堆中申请&#xff1a; static void* ConcurrentAlloc(size_t size) {if (size > MAX_BYTES){size_t alignSize SizeClass::RoundUp(size);size_t kpage alignSize >> PAGE_SHIFT;PageCache::…

数据隐私保护的方法有哪些?

数据隐私保护的方法有哪些&#xff1f; 安企神U盘管理系统下载使用 互联网时代的到来&#xff0c;给我们的生活带来极大的方便&#xff0c;但也给我们保护隐私数据带来巨大的挑战&#xff0c;数据隐私保护是确保个人或企业数据和敏感信息不被未经授权的访问或滥用的关键问题。…

CPU 与简单模型机实验

实验报告 实验名称&#xff1a; CPU 与简单模型机实验 日期&#xff1a; ----.--.-- 班级&#xff1a; ----------- 学号&#xff1a; ------------ 姓名&#xff1a; ---------- 一、实验目的&#xff1a; 1、 掌握一个简单CPU 的组成原理&#xff1b; 2、 在掌…

驱动定时器

基于GPIO子系统编写LED驱动&#xff0c;编写应用程序进行测试 设置定时器&#xff0c;5秒钟打印一次hello world text.c #include<stdlib.h> #include<stdio.h> #include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #include<…

【数据结构初阶】十、快速排序(比较排序)讲解和实现(三种递归快排版本 + 非递归快排版本 -- C语言实现)

相关代码gitee自取&#xff1a; C语言学习日记: 加油努力 (gitee.com) 接上期&#xff1a; 【数据结构初阶】九、排序的讲解和实现&#xff08;直接插入 \ 希尔 \ 直接选择 \ 堆 \ 冒泡 -- C语言&#xff09;-CSDN博客 常见排序算法的实现&#xff08;续上期&#xff09; …

AT800(3000) +昇腾300V 之 第一个例子图片分类

第一个列子 背景开发流程准备模型开发推理流程编码 编译与运行 背景 第一个例子是 图片分类的应用 因第一个&#xff0c;直接获取已训练好的开源模型&#xff0c;选择Caffe框架的ResNet-50模型。 ResNet-50模型的基本介绍如下&#xff1a; 输入数据&#xff1a;RGB格式、22…