排序算法:冒泡和快排 摘自网络

冒泡排序

首先我们自己来设计一下“冒泡排序”,这种排序很现实的例子就是:

我抓一把沙仍进水里,那么沙子会立马沉入水底, 沙子上的灰尘会因为惯性暂时沉入水底,但是又会立马像气泡一样浮出水面,最后也就真相大白咯。

 

关于冒泡的思想,我不会说那么官方的理论,也不会贴那些文字上来,我的思想就是看图说话。

那么我们就上图.

           

要达到冒泡的效果,我们就要把一组数字竖起来看,大家想想,如何冒泡?如何来体会重的沉底,轻的上浮?

 

第一步:  我们拿40跟20比,发现40是老大,不用交换。

第二步:  然后向前推一步,就是拿20跟30比,发现30是老大,就要交换了。

第三步:拿交换后的20跟10比,发现自己是老大,不用交换。

第四步:拿10跟50交换,发现50是老大,进行交换。

 

最后,我们经过一次遍历,把数组中最小的数字送上去了,看看,我们向目标又迈进了一步。

static List<int> BubbleSort(List<int> list)
41 {
42 int temp;
43 //第一层循环: 表明要比较的次数,比如list.count个数,肯定要比较count-1次
44 for (int i = 0; i < list.Count - 1; i++)
45 {
46 //list.count-1:取数据最后一个数下标,
47 //j>i: 从后往前的的下标一定大于从前往后的下标,否则就超越了。
48 for (int j = list.Count - 1; j > i; j--)
49 {
50 //如果前面一个数大于后面一个数则交换
51 if (list[j - 1] > list[j])
52 {
53 temp = list[j - 1];
54 list[j - 1] = list[j];
55 list[j] = temp;
56 }
57 }
58 }
59 return list;
60 }

 

快排:

原文地址:http://www.cnblogs.com/morewindows/archive/2011/08/13/2137415.html

 

快速排序由于排序效率在同为O(N*logN)的几种排序方法中效率较高,因此经常被采用,再加上快速排序思想----分治法也确实实用,因此很多软件公司的笔试面试,包括像腾讯,微软等知名IT公司都喜欢考这个,还有大大小的程序方面的考试如软考,考研中也常常出现快速排序的身影。

 

总的说来,要直接默写出快速排序还是有一定难度的,因为本人就自己的理解对快速排序作了下白话解释,希望对大家理解有帮助,达到快速排序,快速搞定。

 

快速排序是C.R.A.Hoare于1962年提出的一种划分交换排序。它采用了一种分治的策略,通常称其为分治法(Divide-and-ConquerMethod)。

该方法的基本思想是:

1.先从数列中取出一个数作为基准数。

2.分区过程,将比这个数大的数全放到它的右边,小于或等于它的数全放到它的左边。

3.再对左右区间重复第二步,直到各区间只有一个数。

 

虽然快速排序称为分治法,但分治法这三个字显然无法很好的概括快速排序的全部步骤。因此我的对快速排序作了进一步的说明:挖坑填数+分治法:

先来看实例吧,定义下面再给出(最好能用自己的话来总结定义,这样对实现代码会有帮助)。

 

以一个数组作为示例,取区间第一个数为基准数。

0

1

2

3

4

5

6

7

8

9

72

6

57

88

60

42

83

73

48

85

初始时,i = 0;  j = 9;   X = a[i] = 72

由于已经将a[0]中的数保存到X中,可以理解成在数组a[0]上挖了个坑,可以将其它数据填充到这来。

从j开始向前找一个比X小或等于X的数。当j=8,符合条件,将a[8]挖出再填到上一个坑a[0]中。a[0]=a[8]; i++;  这样一个坑a[0]就被搞定了,但又形成了一个新坑a[8],这怎么办了?简单,再找数字来填a[8]这个坑。这次从i开始向后找一个大于X的数,当i=3,符合条件,将a[3]挖出再填到上一个坑中a[8]=a[3]; j--;

 

数组变为:

0

1

2

3

4

5

6

7

8

9

48

6

57

88

60

42

83

73

88

85

 i = 3;   j = 7;   X=72

再重复上面的步骤,先从后向前找,再从前向后找

从j开始向前找,当j=5,符合条件,将a[5]挖出填到上一个坑中,a[3] = a[5]; i++;

从i开始向后找,当i=5时,由于i==j退出。

此时,i = j = 5,而a[5]刚好又是上次挖的坑,因此将X填入a[5]。

 

数组变为:

0

1

2

3

4

5

6

7

8

9

48

6

57

42

60

72

83

73

88

85

可以看出a[5]前面的数字都小于它,a[5]后面的数字都大于它。因此再对a[0…4]和a[6…9]这二个子区间重复上述步骤就可以了。

 

 

对挖坑填数进行总结

1.i =L; j = R; 将基准数挖出形成第一个坑a[i]。

2.j--由后向前找比它小的数,找到后挖出此数填前一个坑a[i]中。

3.i++由前向后找比它大的数,找到后也挖出此数填到前一个坑a[j]中。

4.再重复执行2,3二步,直到i==j,将基准数填入a[i]中。

照着这个总结很容易实现挖坑填数的代码:

int AdjustArray(int s[], int l, int r) //返回调整后基准数的位置

{

       int i = l, j = r;

       int x = s[l]; //s[l]即s[i]就是第一个坑

       while (i < j)

       {

              // 从右向左找小于x的数来填s[i]

              while(i < j && s[j] >= x)

                     j--; 

              if(i < j)

              {

                     s[i] = s[j]; //将s[j]填到s[i]中,s[j]就形成了一个新的坑

                     i++;

              }

 

              // 从左向右找大于或等于x的数来填s[j]

              while(i < j && s[i] < x)

                     i++; 

              if(i < j)

              {

                     s[j] = s[i]; //将s[i]填到s[j]中,s[i]就形成了一个新的坑

                     j--;

              }

       }

       //退出时,i等于j。将x填到这个坑中。

       s[i] = x;

 

       return i;

}

 

再写分治法的代码:

void quick_sort1(int s[], int l, int r)

{

       if (l < r)

    {

              int i = AdjustArray(s, l, r);//先成挖坑填数法调整s[]

              quick_sort1(s, l, i - 1); // 递归调用

              quick_sort1(s, i + 1, r);

       }

}

这样的代码显然不够简洁,对其组合整理下:

//快速排序

void quick_sort(int s[], int l, int r)

{

    if (l < r)

    {

              //Swap(s[l], s[(l + r) / 2]); //将中间的这个数和第一个数交换 参见注1

        int i = l, j = r, x = s[l];

        while (i < j)

        {

            while(i < j && s[j] >= x) // 从右向左找第一个小于x的数

                            j--; 

            if(i < j)

                            s[i++] = s[j];

                    

            while(i < j && s[i] < x) // 从左向右找第一个大于等于x的数

                            i++; 

            if(i < j)

                            s[j--] = s[i];

        }

        s[i] = x;

        quick_sort(s, l, i - 1); // 递归调用

        quick_sort(s, i + 1, r);

    }

}

 

快速排序还有很多改进版本,如随机选择基准数,区间内数据较少时直接用另的方法排序以减小递归深度。有兴趣的筒子可以再深入的研究下。

 

注1,有的书上是以中间的数作为基准数的,要实现这个方便非常方便,直接将中间的数和第一个数进行交换就可以了。

 

转载于:https://www.cnblogs.com/liujin2012/archive/2013/04/08/3008339.html

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

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

相关文章

镭波笔记本安装linux,镭波笔记本windows7旗舰版系统下载与安装教程

镭波笔记本windows7旗舰版系统下载地址以及安装教程有很多盆友询问&#xff0c;今天&#xff0c;我就将镭波电脑下载安装win7旗舰版系统的详细步骤分享给你们,一起来了解一下镭波电脑是如何安装windows7旗舰版。镭波笔记本Windows7旗舰版系统下载&#xff1a;64位Windows7旗舰版…

全国计算机等级考试题库二级C操作题100套(第85套)

第85套&#xff1a; 给定程序的功能是调用fun函数建立班级通讯录。通讯录中记录每位学生的编号、姓名和电话号码。班级的人数和学生的信息从键盘读入,每个人的信息作为一个数据块写到名为myfile5.dat的二进制文件中。 请在程序的下划线处填入正确的内容并把下划线删除&#xf…

使用泛型解决之前的问题

package fanxing; /* * 使用泛型解决之前的问题 */ import java.util.ArrayList;import java.util.Iterator;import java.util.LinkedList; public class TestGeneric02 { public static void main(String[] args) { LinkedList<Integer> list new LinkedList<>()…

python中文姓名排序_Python实现针对中文排序的方法

本文实例讲述了Python实现针对中文排序的方法。分享给大家供大家参考&#xff0c;具体如下&#xff1a;Python比较字符串大小时&#xff0c;根据的是ord函数得到的编码值。基于它的排序函数sort可以很容易为数字和英文字母排序&#xff0c;因为它们在编码表中就是顺序排列的。但…

网站数据库中“密码加密”方法思考

博主&#xff0c;开始时候&#xff0c;写的web应用&#xff0c;数据库中的密码&#xff0c;都是直接保存的。真正的原汁原味&#xff0c;真正的所见即所得。 后来&#xff0c;看了别人的web应用都是MD5加密的&#xff0c;感觉很不错&#xff0c;自己也在应用中加入了MD5加密&am…

linux运维和3dmax哪个简单,牛逼运维常用的工具系列-2

劳动最光荣nmonnmon是linux性能监视和分析数据的工具&#xff0c;它的安装很简单&#xff0c;下载解压后&#xff0c;添加可执行权限&#xff0c;即可运行下载解压后&#xff0c;通过文件名可以发现&#xff0c;是多个发行版本的&#xff0c;根据自己的发行版本&#xff0c;然后…

全国计算机等级考试题库二级C操作题100套(第86套)

第86套&#xff1a; 甲乙丙丁四人同时开始放鞭炮&#xff0c;甲每隔t1秒放一次&#xff0c;乙每隔t2秒放一次, 丙 每隔t3秒放一次&#xff0c;丁每隔t4秒放一次&#xff0c;每人各放n次。函数fun的功能是根据形参 提供的值&#xff0c;求出总共听到多少次鞭炮声作为函数值返回…

语义分割和实例分割_语义分割入门的一点总结

点击上方“CVer”&#xff0c;选择加"星标"或“置顶”重磅干货&#xff0c;第一时间送达作者&#xff1a;Yanpeng Sunhttps://zhuanlan.zhihu.com/p/74318967本文已由作者授权&#xff0c;未经允许&#xff0c;不得二次转载语义分割目的&#xff1a;给定一张图像&…

【转载】什么是C++虚函数、虚函数的作用和使用方法

我们知道&#xff0c;在同一类中是不能定义两个名字相同、参数个数和类型都相同的函数的&#xff0c;否则就是“重复定义”。但是在类的继承层次结构中&#xff0c;在不同的层次中可以出现名字相同、参数个数和类型都相同而功能不同的函数。例如在例12.1&#xff08;具体代码请…

linux 音频驱动的流程,Intel平台下Linux音频驱动流程分析

【软件框架】在对要做的事情一无所知的时候&#xff0c;从全局看看系统的拓扑图对我们认识新事物有很大的帮助。Audio 部分的驱动程序框架如下图所示&#xff1a;这幅图明显地分为 3 级。上方蓝色系的 ALSA Kernel 整体属于Linux Kernel&#xff0c;是原生Linux 操作系统的一部…

Windows Server 2008 R2Cisco2960 配置Radius服务 实现802.1x认证 实战

实战配置Windows Server 2008 R2 Radius服务 与Cisco 2960 实现 802.1x认证实验拓扑1.Radius服务器 安装 dc 域名 wjl.com &#xff0c;和ca 安装步骤不再详解2.安装完ca之后&#xff0c;打开MMC 添加计算机证书&#xff0c;查看个人-证书里面有没有ca颁发给计算机的证书&…

python多线程下载器_用 python 实现一个多线程网页下载器

学习之#!/usr/bin/env python# -*- coding:utf-8 -*-import urllib, httplibimport threadimport timefrom Queue import Queue, Empty, FullHEADERS {"Content-type": "application/x-www-form-urlencoded",Accept-Language:zh-cn,User-Agent: Mozilla/4…

全国计算机等级考试题库二级C操作题100套(第87套)

第87套&#xff1a; 函数fun的功能是&#xff1a;统计长整数n的各个位上出现数字1、2、3的次数,并通过外部(全局)变量c1&#xff0c;c2&#xff0c;c3返回主函数。例如&#xff1a;当n123114350时&#xff0c;结果应该为: c13 c21 c32。 请在程序的下划线处填入正确的内容并把…

Linux命令之ifconfig

ifconfig [interface] ifconfig interface [aftype] options | address… ifconfig是用来查看和配置网络接口的工具。Ifconfig配置的信息在网络设备重启后&#xff0c;配置就会还原。需要永久保存&#xff0c;请进入配置文件配置。 address可以是inet&#xff08;TCP/IP&#x…

C#实现RTP数据包传输

闲暇时折腾IP网络视频监控系统&#xff0c;需要支持视频帧数据包在网络内的传输。未采用H.264或MPEG4等编码压缩方式&#xff0c;直接使用Bitmap图片。由于对帧的准确到达要求不好&#xff0c;所以采用UDP传输。如果发生网络丢包现象则直接将帧丢弃。为了记录数据包的传输顺序和…

linux文件编程(3)—— main函数传参、myCp(配置成环境变量)、修改配置文件、将整数和结构体数组写到文件

参考&#xff1a;linux文件编程&#xff08;3&#xff09;—— 文件编程的简单应用&#xff1a;myCp、修改配置文件 作者&#xff1a;丶PURSUING 发布时间&#xff1a; 2021-04-09 23:45:05 网址&#xff1a;https://blog.csdn.net/weixin_44742824/article/details/115209404 …

51芯片4*4列阵按键c语言程序,单片机城中社稷.doc

单片机城中社稷基于单片机的乳粉包装称重控制设计摘 要本论文在分析了国内外称重技术发展的基础上&#xff0c;着重对一个用于工业控制且功能较齐全的自动称重系统进行设计。随着自动化和管理现代化的进展&#xff0c;自动在线称重&#xff0c;快速动态称重在整个称重系统中有了…

linux 修改文件名_Linux常用命令

Linux下一切皆文件查看型ls 查看当前文件夹内容 选项 -a 查看隐藏文件 -l 查看文件详细信息pwd 查看当前所在路径su 切换用户cat /etc/passwd 查看当前系统的用户cat 文件 查看文件内容选项 -n 加上编号 -E 每行末尾加上$ifconfig 查看网卡名&#xff0c;IP地址等网络信息route…

Redis学习日记-05:SORT命令

目录 前言命令&选项SORT&#xff08;默认根据元素由小到大&#xff09;&#xff1a;DESC&#xff08;逆序&#xff09;&#xff1a;ALPHA&#xff08;非数字元素排序&#xff09;&#xff1a;BY&#xff08;参考键&#xff09;&#xff1a;LIMIT(返回指定范围的结果)&#…

Cocos2d-x Eclipse下程序运行产生错误Effect initCheck() returned -1

错误大致显示如下信息&#xff1a;04-14 07:39:18.325: E/AudioEffect(20584): set(): AudioFlinger could not create effect, status: -104-14 07:39:18.325: E/libOpenSLES(20584): Effect initCheck() returned -104-14 07:39:18.325: E/libOpenSLES(20584): Environmental…