排序算法第二辑——选择排序

一,选择排序

选择排序算是简单排序中的渣渣,这种算法基本上是没有什么用处的。但是作为一个初学者,我又必须要会写这种算法。这种算法的实现实现思想和它的名字一样,就是在一个范围内选择最大或者最小的数据然后再交换数据实现排序。比如我有如下数据需要排序:

将数据具象化以后变成这样:

 现在我们可以选择的范围是哪些呢?

范围:  begin:0                    end:n-1。

 

 然后我们要在这个范围内选择最大的数据或者最小的数据与尾/首的数据进行交换,再将选择范围缩小:

先设置begin的后一个为最小值,end的前一个为最大值然后遍历调整得到真的最大和最小值的下标。然后将最小值和begin指向的位置交换,最大值和end指向的下标的值交换。用这个逻辑不断地走,不断地缩小查找范围,当查找范围没了(即end>=begin不再成立)以后排序就完成了。

代码:

void swap(int* p1, int* p2)
{int tmp = *p1;*p1 = *p2;*p2 = tmp;
}
void selectSort(int* a, int n)
{   //初始的查找范围int end = n - 1;int begin = 0;//while循环判断查找空间是否还有while (begin <= end){  //实现交换逻辑int maxi = end-1;int mini = begin+1;for (int i = begin;i <= end;i++){if (a[i] > a[maxi]){maxi = i;}if (a[i] < a[mini]){mini = i;}}swap(&a[maxi], &a[end]);//处理特殊情况:当mini与end指向同一数据时需要处理一下if (mini == end){mini = maxi;}swap(&a[mini], &a[begin]);//缩小查找范围end--;begin++;}}

 二,堆排序

堆排序,也是选择排序的一种。但是堆排序的速度比原始的选择排序快多了。

比如下面的数据:

如果使用堆排序的话就要先将这些数据看成满二叉树的结构:

然后就要建堆了:

建堆原则:排升序建大堆,排降序建小堆。

建堆(排升序)变成这样:

 建堆完成以后便要执行下面的操作:

1.交换首尾数据。

2.缩小范围。

3.向下调整。

经过这几步以后堆排序就写好了。

堆排序代码:

void AdjustDown(int* a, int n,int parent)
{int child = 2 * parent + 1;while (child < n){if (child + 1 < n && a[child + 1] > a[child]){child++;}if (a[child] > a[parent]){swap(&a[parent], &a[child]);}parent = child;child = parent * 2 + 1;}}
void heapSort(int* a, int n)
{//向下调整建堆for (int i = (n - 1 - 1) / 2;i >= 0;i--){AdjustDown(a, n,i);}int end = n - 1;for (int i = end; i > 0;i--){   //交换首尾数据swap(&a[end], &a[0]);//向下调整AdjustDown(a, end, 0);//缩小调整范围end--;}
}

 三,性能比较

堆排序是一个很好的算法,选择排序是一个很慢的算法。但是口说无凭,现在就写一段代码来验证这个事实。

代码:

void test()
{   //创建两个数组并将两个数组内的数据搞成随机值srand(time(0));int n = 100000;int* a1 = (int*)malloc(sizeof(int) * n);int* a2 = (int*)malloc(sizeof(int) * n);int i = 0;for ( i = 0;i < n;i++){int j = rand();a1[i] = j;a2[i] = a1[i];}//记录选择排序的时间int begin1 = clock();selectSort(a1, n);int end1 = clock();//记录堆排序的时间int begin2 = clock();heapSort(a2, n);int end2 = clock();//打印两个排序的时间printf("selectSort:%d\n", end1 - begin1);printf("heapSort:%d\n", end2 - begin2);//释放内存free(a1);free(a2);
}

排十万个数据的时间:单位(ms)

selectSort:5051
heapSort:30

从结果可以看到堆排序的效率暴打选择排序。

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

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

leetcode 98. 验证二叉搜索树

2023.7.9 这题有个陷阱&#xff0c;就是不能单纯的比较左节点小于中间节点&#xff0c;右节点大于中间节点就完事了。我们要比较的是 左子树所有节点小于中间节点&#xff0c;右子树所有节点大于中间节点。 我的思路是先用中序遍历所有节点&#xff0c;并将其放入数组中&#…

如何用ChatGPT做咨询师,附Prompt

对基本问题研究得不深不透、得不到可靠的分析框架支持的情况下&#xff0c;仓促采取就事论事的应对措施 &#xff0c;由于未能触及事情的根本&#xff0c;往往非但不能获得预期的效果&#xff0c;相反可能引发新的矛盾。 ——吴敬琏&#xff08;著名经济学家&#xff0c;国务院…

途乐证券-主力砸盘是什么意思?和洗盘有什么区别?

投资者在进行股票交易的过程中&#xff0c;经常会听说主力出货、洗盘以及砸盘等等操作但是不了解是什么意思。那么主力砸盘是什么意思&#xff1f;和洗盘有什么区别&#xff1f;下面就由途乐证券为我们分析&#xff1a; 主力砸盘是什么意思&#xff1f; 主力砸盘便是主力在股票…

uniapp 小程序 vue TypeError: Cannot read property ‘toString‘ of undefined

是因为对字符串使用toString的时候页面中的数据还没有加载 。错误代码&#xff1a; 可以使用 v-if 修改为&#xff1a;

Qt6之QSetting读取为空或失败

一、目的 QSetting终极目的是&#xff0c;模糊平台&#xff0c;一套方法可以同时写入或者读取配置文件及注册表。 二、问题 QSetting确实兼顾了平台&#xff0c;linux、mac、windows三大平台均能使用&#xff0c;但就像所有事物一样&#xff0c;大一统的背后必定要做出一些让步…

【新星计划·2023】认识和学习BASH(一)

作者&#xff1a;Insist-- 个人主页&#xff1a;insist--个人主页 作者会持续更新网络知识和python基础知识&#xff0c;期待你的关注 目录 一、认识BASH 1、硬件、核心与Shell ①硬件 ②核心管理 ③应用程序 2、为何要学文字接口的shell&#xff1f; 3、系统的合法shel…

基于java+servlet+mysql-图书商城

基于javaservletmysql-图书商城 一、系统介绍二、功能展示1.项目骨架2.首页3.图书详情4.我的订单5.我的购物车6、注册7、登录8、图书管理9、订单管理 四、其它1.其他系统实现五.获取源码 一、系统介绍 项目类型&#xff1a;Java web项目 项目名称&#xff1a;基于javaservlet…

快速排序的三种方法

快速排序是Hoare于1962年提出的一种二叉树结构的交换排序方法&#xff0c;其基本思想为&#xff1a;任取待排序元素序列中的某元素作为基准值&#xff0c;按照该排序码将待排序集合分割成两子序列&#xff0c;左子序列中所有元素均小于基准值&#xff0c;右子序列中所有元素均大…

Vscode 绿色系清新主题

炎炎夏日&#xff0c;上班上的心浮气躁&#xff0c;敲代码的时候&#xff0c;只觉昏昏沉沉&#xff0c;浑浑噩噩... 给vscode换一个一个清新美好的绿色主题&#xff0c;充满活力和希望吧。 朋友们&#xff0c;收藏起来&#xff0c;每个季节换一个主题&#xff0c;打工快乐&am…

Linux查找关键字出现的位置

在Linux中&#xff0c;您可以使用以下命令来查找文件中关键字出现的位置&#xff1a; grep -rnw /path/to/search -e keyword其中&#xff1a; - -r 递归地搜索指定路径下的所有子目录。 - -n 显示匹配行的行号。 - -w 完整匹配单词&#xff0c;而不是部分匹配。 - /path/to/s…

ubuntu安装单个redis服务

1.apt-get install redis-server 使用lighthouse用户这样操作会报与权限有关的错误&#xff0c; 改成使用root账号操作 2.安装完成后&#xff0c;Redis服务器会自动启动&#xff0c;查看进程是否正常启动 ps -axu|grep redis redis 18689 0.1 0.4 40136 6860 ? …

Spark(20):SparkStreaming之概述

目录 0. 相关文章链接 1. Spark Streaming 是什么 2. Spark Streaming 的特点 2.1. 易用 2.2. 容错 2.3. 易整合到Spark体系 3. Spark Streaming 架构 3.1. 架构图 3.2. 背压机制 0. 相关文章链接 Spark文章汇总 1. Spark Streaming 是什么 Spark 流使得构建可扩展的…