zoukankan      html  css  js  c++  java
  • 选择排序

    前面我们探讨了冒泡排序,今天我们接着讲讲选择排序,其实跟冒泡有点像的,但概念上不一样,童鞋,你听我慢慢跟你说。

    什么是选择排序?

    引言

    最近看了一则寓言故事跟童鞋们分享一下,讲的是大山深处的神坑(为了激发大家的想象力,这里我就不画画了,请同学们自行脑补)。事情是这样子的,旁白站在上帝视角抛出一个上帝之问?为什么穷人努力工作还是越来越穷,生活不见起色,而富人却越来越富。一天,他们一同去爬山,这里我们先不考虑“推下去”这个梗,毕竟张东升他没去。当他们快到达山顶的时候,穷人看见前面的大坑,发现自己迈不过去,于是他找来了推车,一车子一车子地推石头子,打算把它填满,推的精疲力竭啊,一不小心脚绊倒了石头,连车带石头都掉进了神坑,这个时候他很苦恼,家里还有老还有小,我要努力我不能放弃啊,于是他又用双手搬石头一块一块地去填。此时,富人推着一个圆滚滚的巨石,将它推入坑中,因为直径比坑大,所有刚好卡在了上面,富人巧妙地通过了神坑。这个故事告诉我们,努力是没有错的,它也很重要,当你努力到一定程度就会由量变引起质变,但很多时候啊,选择大于努力。我们的一生会遇到很多的苦难和险阻,有坑在所难免,面对前方的未知,谁不怕呀!关键是我们要怎样去做好选择,走好每一步,这就引出了我们今天的话题“选择排序”。

    定义

    上面的故事,穷人和富人做的选择不一样,穷人做了很多次选择,选的都是比坑小的石头,而富人有其得道的见解,选了一块巨石去把坑给堵住了。再理解这个选择以后呢,我们再进一步做个游戏。

    结合上面选择的案例思想,给定五块随机排列的石头,请你想一种办法,让他们由小到大排列。

    我们是不是可以这样子去做,第一次,我找出了最小的那块石头,我把它和第一个位置的选手交换位置,第二次,我从第二个位置开始找一块最小的石头,找到后和第二个位置交换一下,以此类推,这个问题是不是就解决了啊。

    所有,我们给出一个定义,给定一组数据集,对这组数据集进行遍历、每次从对应下标开始往后遍历找出最小的那位,将其与最开始的下标所在元素进行交换位置,形如这样的排序,我们将其称为“选择排序”。

    实现一个选择排序

    思路: 我们可以先假定那个min为最开始的那个元素,然后记录其下表进行遍历,当找到最小的那个元素之后,我们把min假定为最小元素后面那个,然后更新下标,以此类推,所以其平均复杂度是O(n^2)

    code:

    export default (arr) => {
      let min = arr[0];
      let idx = 0;
      for (let i = 0; i < arr.length - 1; i++) {
        for (let j = i + 1; j < arr.length; j++) {
          if (min > arr[j]) {
            min = arr[j];
            idx = j;
          }
        }
        [arr[i], arr[idx]] = [min, arr[i]];
        [min, idx] = [arr[i + 1], i + 1];
      }
      return arr;
    }
    

    test:

    这里笔者准备了几个测试用例,测试都通过了,这个排序应该没啥问题。

    test case:

    import selectSort from '../src/select';
    
    test('select sort: test case 1', () => {
      expect(selectSort([2, 4, 3, 1])).toEqual([1, 2, 3, 4]);
    });
    
    test('select sort: test case 2', () => {
      expect(selectSort([2, 0, 2, 0])).toEqual([0, 0, 2, 2]);
    });
    
    test('select sort: test case 3', () => {
      expect(selectSort([1, 9, 9, 7])).toEqual([1, 7, 9, 9]);
    });
    
    test('select sort: test case 4', () => {
      expect(selectSort([0, 6, 1, 3])).toEqual([0, 1, 3, 6]);
    });
    

    test result:

    PS E:document
    eposJavaScript-Tsukukicodesort-study> npm run test:select
    
    > sort-study@1.0.0 test:select E:document
    eposJavaScript-Tsukukicodesort-study
    > jest test/select.test.js
    
     PASS  test/select.test.js
      √ select sort: test case 1 (15 ms)
      √ select sort: test case 2
      √ select sort: test case 3
      √ select sort: test case 4
    
    Test Suites: 1 passed, 1 total
    Tests:       4 passed, 4 total
    Snapshots:   0 total
    Time:        7.013 s
    Ran all test suites matching /test\select.test.js/i.
    PS E:document
    eposJavaScript-Tsukukicodesort-study> 
    

    emmm, 这里我是测试和开发分开写的,有兴趣可以阅读我之前写的jest的使用https://www.cnblogs.com/cnroadbridge/p/13524099.html

    优化选择排序

    跟之前讲的冒泡排序一次冒两个泡泡一个道理,你一次选择两个,一个最大一个最小,最大的与最后一个元素换位置,最小的与最前面的换位置,一个道理,有兴趣的童鞋自己实践下。

    最后

    本文选自Javascript筑基专题文章,项目地址:https://github.com/ataola/JavaScript-Tsukuki

    知识共享许可协议
    本作品采用知识共享署名-非商业性使用-相同方式共享 4.0 国际许可协议进行许可。

  • 相关阅读:
    GNU KHATA——开源的会计管理软件
    Web服务精讲–搭个 Web 服务器(二)
    据说Linuxer都难忘的25个画面
    谷歌开源运作解密
    实战Centos系统部署Codis集群服务
    这些被称为史上最 “贱” 黑客
    Linux 利器- Python 脚本编程入门(一)
    在 Ubuntu 16.04 上安装 LEMP 环境之图文向导
    Linux下6种优秀的邮件传输代理
    移动互联网期末笔记
  • 原文地址:https://www.cnblogs.com/cnroadbridge/p/13586287.html
Copyright © 2011-2022 走看看