给一万个士兵排个序---基础排序算法随记

不想当将军的士兵,不是好士兵。不了解算法的程序员也不是好的程序员。

                                                                                    by   尼古拉斯---彦祖

首先给上一张,实验环境下,各个排序算法的时间效率对比。

实验环境下的排序结果



一  简单概念

    算法频率度即一个算法中的语句执行次数称为语句频度或时间频度。记为T(n)

    时间复杂度以大O表示法 常见的有四种:

    O(1)、O(n)、O(logn)、O(n²)分别可以称为常数阶线性阶对数阶平方阶


二  快速排序


    取某一位(一般是首位)作为flag. 分治法排序。

    每一趟的下标都是前后同时进行,比flag小的放到左边,比flag大的放到右边。结束条件为前后下标重合。

    一趟排序可以得到以flag为界限的 两个集合。依次递归,结束条件为不可再分。



    换句话说:  现在要给一万个排成一列的士兵 按照大小个排队。  

    首先取第一个士兵的高度为标准,称其为flag,一趟算法的期望运行结果,就是所有比这个士兵低的人在这个士兵前面,所有比这个士兵高的人都在他后面。

    那么,怎么实现这个效果呢?? 

    找两个将军来,一个站在列首,一个站在列尾。

    列尾的将军,站在第10000个士兵这个位置,看看他比flag高,还是低,如果高那么不管,列尾的将军向前走一步。 走到第9999个士兵处,继续比较,直到走到一个比flag低的士兵位置。比如第9996个士兵比第一个士兵低,那么让 9996和 1 互换位置。     此时的flag的位置变成了9996

    现在列尾的将军先休息,让列首的将军从2这个位置向前走,走到第一个比flag高的位置,比如是第15个。 那就让15 和9996换位置,并且更新flag为15。此时列首将军休息,列尾的将军继续。  以此类推。

直到列首和列尾的将军碰了面,那么本趟快排结束。 

比如此时的位置是6666个士兵处。根据上面的过程推论,此时flag也一定在6666处。两个将军不碰面也正是快速排序的特点

那么本趟排序完成。 整个队列被6666分成了两个A B队列,前面的一定比士兵flag矮小,后面的一定比flag高大。

然后再请四位将军过来对,这AB两个队列进行上述操作。直到队列变成2个人(不可再分割)。以此类推

快排执行效率



快排源码实现


三   选择排序


    与冒泡排序类似,但是区别在于,新建局部变量储存本趟的目标值。

    每次只比较而不交换,直到一趟排序结束之后。才进行转换,提升了部分效率


    还是那一列一万个士兵的队伍。 

    一个将军拿着一个笔记本,

    从第一个开始问,你身高多少? “1.60”   看来你是最低的,于是他将第一个士兵的名字写到了笔记本上。

    第二个 “你身高多高”    “185”     不管,下一个

    第三个问“你身高多少”“158”        将军,划掉了上一个名字,记上了最新的这个人的名字。

    直到问完整个队伍。  将军看到笔记本上写着  最低的那个人的名字   “提利昂-兰尼斯特”  你站到第一个位置。

    这是一趟排序结束。


     接下来,将军从第二个位置开始问。(第一个已经确定了)以此类推,直到最后一个。

    


选择排序比冒泡排序快很多    


选择排序实现

四  插入排序


    4.1 简单插入排序

        简单插入排序的核心思想是认为,所有的事情都是基于一个已有序的序列进行的。

        比如下标从第一个元素开始,认为  第一个元素本身是一个有序序列(这是对的,因为只有一个元素。)

        那么下标转移到第二个元素,将第二个元素 去与左边的有序序列(第一个元素)比较,插入到合适的位置。

        下标继续,逻辑依然如此,直到下标行走到最后的位置。整个序列都有序了。


        他的算法逻辑是这样的, 请来两位将军A,B, 

        首先是告诉A将军,你首先管理的是无序的9999个士兵队列。你只管把他们一个个都推出去给B将军就行了。 你可以认为B将军那里的永远是一个有序队列。

        然后告诉B将军,你手下永远是有序的队列。现在你手下有一个人,当然是有序的,接下来再来新人,都让他们和之前的有序队列比较,找到他们合适的位置。  

        第二个人来的时候,和原先的第一个人比较,如果比之前的人高,那么站在他后面,如果比他矮站在他前面 

        第三个人来的时候,从第一个位置开始找,找到第一个比他高的人,插入进队列。后面的士兵,都后退一步。


        以此类推,直到B将军手下 所有的士兵都到了A将军手下为止。

        所以,你可以简单的理解它为插队排序



    4.2  希尔排序

        希尔排序是基于插入排序的以下两点性质而提出改进方法的:

            1     插入排序在对几乎已经排好序的数据操作时,效率高,即可以达到线性排序的效率。

            2     但插入排序一般来说是低效的,因为插入排序每次只能将数据移动一位。


        希尔排序的意思是现将正序列变成一个基本有序的序列,然后再进行简单插入排序。

        那么如何将一个序列变成基本有序的序列呢。 现在有一个100元素的序列


        第一趟将其拆成50个有序序列。  对这50个有序序列进行简单插入排序

        第二趟将其拆分为25个,每个4元素的序列,对这25个有序序列进行简单插入排序。

        知道最后将其拆分为一个 100元素序列为止。


        希尔排序是在简单插入排序的基础上演进来的,理论的东西,不多赘述。可以这样理解。

        希尔排序的基本思想还是 A ,B两个将军 分别管理一个有序队列和一个无序队列。

        但是差别在于,如果整个队列是接近完全无序的情况下,每次新兵进去 B将军的有序队列,都要进行一次整体的位移。也就是比较的次数为LOG(n2),而且在排序后期,这里的N基本都无限接近一万,这是一个很大的性能消耗。

        而希尔排序,则是先取增量为10,所有的下标向10取余

        先让尾号为0的士兵向前一步, 这样就出现了1000名,位置尾号为0的士兵。 先对这1000名士兵进行插入排序,即便出现插入操作而导致的整体位移,移动成本也比一万名士兵移动好多了。  这样已经有十分之一的士兵有序了

        然后再让尾号为1的士兵向前一步...,尾号为2的士兵向前一步。  以此类推。整体一万个士兵也就基本有序了。


这样我们一趟排序完成,此时我们的增量为10. 接下来我们降低增量为5,

所有士兵的下标向5取余。  我们还是按照刚才的办法,每次对五分之一的士兵,进行插入排序。

虽然两千名士兵整体位移的成本依然很高,但是毕竟比一万小了很多,况且之前已经有过一次十分之一规模的插入排序了。所以发生插入操作的概率不大。

第二趟排序结束。  继续缩小增量。直到为0.。。。。。   

over (真特么的麻烦。。。)


希尔排序执行效果




希尔排序代码实现

五  冒泡排序

    相对原始的方法,对比每一个元素,每趟选出一个最大值出来。时间复杂度为O(n2)


这个算法最简单,也最好理解,和选择排序极为类似。只不过区别不是将军带着笔记本去挨个统计个头了。

而是将军领着当前等待排序的士兵本人,与下一个士兵比个头。  最后跟着将军走到队列尾部的,一定是个头最大的。

    算法实现:


冒泡




附上:源码下载地址:

http://note.youdao.com/noteshare?id=2afb3adfc83d0684ff79deb931c079bb&sub=97381DA724BC4B3DA8EE2D5175176593

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 215,794评论 6 498
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 92,050评论 3 391
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 161,587评论 0 351
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 57,861评论 1 290
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 66,901评论 6 388
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 50,898评论 1 295
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 39,832评论 3 416
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 38,617评论 0 271
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 45,077评论 1 308
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 37,349评论 2 331
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 39,483评论 1 345
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 35,199评论 5 341
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 40,824评论 3 325
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 31,442评论 0 21
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 32,632评论 1 268
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 47,474评论 2 368
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 44,393评论 2 352

推荐阅读更多精彩内容

  • 概述 因为健忘,加上对各种排序算法理解不深刻,过段时间面对排序就蒙了。所以决定对我们常见的这几种排序算法进行统一总...
    清风之心阅读 695评论 0 1
  • 排序算法基础 排序算法,是一种能将一串数据按照特定的排序方式进行排列的一种算法,一个排序算法的好坏,主要从时间复杂...
    jackyshan阅读 3,940评论 3 11
  • 作者:大海里的太阳原文地址:http://www.cnblogs.com/wxisme/ 前言 查找和排序算法是算...
    IT程序狮阅读 2,498评论 0 63
  • 古之学者为己,今之学者为人。 孔子如是说。古代学习的人为修养自身而学,现在的人为取悦他人而学。 他口中的“今人”应...
    锦瑟_db50阅读 319评论 0 0
  • 01 你用笔写过信吗?或者,你多久没有亲自写过一封信了? 反正我是很久很久了,自从有了电脑,有了手机,一个电话,一...
    少女素子阅读 705评论 0 1