基础数据结构-递归实现插入排序-Java
  rvbXLx8myZeQ 2023年12月15日 64 0

一、思想-什么是插入排序

插入排序是一种最简单直观的排序算法,它的工作原理是通过构建有序序列,对于未排序数据,在已排序序列中从后向前扫描,找到相应位置并插入。和打扑克牌时整理牌类似,假设你拿到的牌中有一个顺子,但是刚拿到的牌是乱序的,你需要将它整理好,也就是进行一个排序,你可以这样整理:从一张牌开始,拿它后面的牌和它进行比较,若后面的牌小于前面的牌,则将后面这张牌拿出来插入到它前面这张牌的前面,这样就是插入排序,不断地重复这个过程就可以将你的顺子整理好了。

二、例子

基础数据结构-递归实现插入排序-Java_插入排序

基础数据结构-递归实现插入排序-Java_递归_02

一个数组,我们可以分成已排序部分和非排序部分,现在我们要将非排序部分中的一个元素插入到已排序部分中。

现在我们将数组中的第一个元素(索引=0)设置为已排序部分的上边界,让一个指针i指向它。此元素后面的部分属于未排序区域,给一个指针low指向这个未排序区域的下边界(索引=1)。这两个指针的关系是i = low - 1,它们是相邻的。

排序的时候我们就选取low指针指向的元素与i指针指向的元素进行比较。先将low指针指向的元素放到一个临时变量t里面(因为等会进行比较的时候low指向的索引位置可能会被覆盖掉,这是为了给要插入的元素腾出一个位置,相当于我们把牌拿出去之后再放进来。)。

若low指向的元素大于i指向的元素,则a[i+1] = t,然后继续递归,继续调用函数insertion(a,low + 1),注意此时low已经变成了low+1,也就是说未排序部分的下边界已经右移了一位;

若low指向的元素小于i指向的元素,则a[i + 1] = a[i],将索引为i的元素的值赋值给索引为i+1的元素,注意这个时候a[i+1]就被覆盖掉了,而我们前面说过i = low - 1,那么low = i + 1,也就是这个low指向的元素被覆盖了,所以我们前面要设置一个临时变量来保存a[low]的值,接下来i--,即指针i左移,继续来寻找比t小的值。

当i<0时退出循环,执行下面的a[i + 1] = t,这时i = -1,所以有a[0] = t,意思就是将这个t放在了第一位。

随着我们的递归不断地进行,已排序的区域就会不断地增大,未排序的区域就会不断地缩小,直到最后我们将元素全部都排好序。

结束递归的条件就是未排序部分的下边界等于数组长度。

三、Java代码实现

1.递归部分-我们先写出递归的框架

  /*写一个递归函数insertion 它接受两个参数
    * 1.int[] a整个需要进行排序的数组
    * 2.int low未排序区域的下边界 */
private static void insertion(int[] a,int low){
        /*low等于数组长度时,我们就停止递归,这里是递归出口*/
        if(low == a.length){
            return;
        }
        /*当low小于数组长度时,继续进行递归,未排序区域的边界向右移*/
        insertion(a,low + 1);
    }

2.排序部分-排序的实现

        /*先将low指针指向的变量的值存储到一个临时变量里面,
        目的是之后我们要用它与已排序区域中元素的值进行比较,
        因为a[i + 1] = a[i];之后low这个位置就会被覆盖掉。
        比较之后我们才能确定这个元素的插入位置*/
        int t = a[low];
        int i = low - 1;/*变量i代表已排序区域的一个指针,low - 1就是已排序区域的上边界*/
        /*从已排序部分的右边相左找,就能找到第一个比t小的元素,然后就能将t插入了*/
        
        while(i >= 0 && a[i] > t){//没有找到要插入的位置时,不断进行循环,直到找到为止
            a[i + 1] = a[i];//空出插入位置
            i--;//指针i 左移
        }
        a[i + 1] = t;//a[i] < t 时退出循环,找到了插入位置

3.完整代码

    /*我们可以对外暴露一个更容易使用的函数sort
    * 这里的sort函数只接收一个参数int[] a
    * 在sort里面我们再来调用insertion函数,未排序下边界我们设置为1.*/
    public static void sort(int[] a){
        insertion(a,1);
    }

    /*insertion函数,用来进行递归插入排序*/
    private static void insertion(int[] a,int low){
        if(low == a.length){
            return;
        }
        
        int t = a[low];
        int i = low - 1;

        while(i >= 0 && a[i] > t){
            a[i + 1] = a[i];
            i--;
        }
        a[i + 1] = t;

        insertion(a,low + 1);
    }
}




【版权声明】本文内容来自摩杜云社区用户原创、第三方投稿、转载,内容版权归原作者所有。本网站的目的在于传递更多信息,不拥有版权,亦不承担相应法律责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@moduyun.com

  1. 分享:
最后一次编辑于 2023年12月15日 0

暂无评论

推荐阅读
rvbXLx8myZeQ