几种简单排序算法(Java实现)

冒泡排序

思想

冒泡排序,又称下沉排序,其大致思路为:
在一个整数序列中,两两进行比较,若前者大于后者,则两者交换位置,若后者大于前者,则保持不变继续进行比较。在进行完一次冒泡后,则会将最大元素放至序列最后。序列中有多少数据,就需要进行多少趟冒泡。
示例如下
在这里插入图片描述

代码

代码实现:

    public static void bubbleSort(int[] array){
        //参数合法性判断
        if(array == null||array.length==0){
            return;
        }
        //时间复杂度 不包含系数 O(n^2)
        //空间复杂度  O(1)
        //稳定性  1 2 2' 0 5 -》0 1  2 2' 5 稳定
        //冒泡的趟数
        for(int i = 0;i<= array.length-1;i++){
            //一趟冒泡的过程
            for(int j=0;j< array.length-i-1;j++){   //每次比较的数据都比上一躺少一个
                if(array[j]>array[j+1]){
                    int tmp = array[j];
                    array[j] = array[j+1];
                    array[j+1] = tmp;
                }
            }
        }
    }

我们观察到以上代码可以实现冒泡排序,但是如果进行完几次排序后,剩下的数组本来就有序,导致整个序列已经有序,此时代码仍会执行,就会浪费时间和空间,为了解决这个问题,我们可以定义一个布尔类型变量,初始化为false,若执行了交换位置操作再赋值为true,就可以在数组有序时停止循环。优化后代码如下:

    public static void optimizedbubbleSort(int[] array){
        //参数合法性判断
        if(array == null||array.length==0){
            return;
        }
        //时间复杂度 不包含系数 O(n^2)
        //空间复杂度  O(1)
        //稳定性  1 2 2' 0 5 -》0 1  2 2' 5 稳定
        //冒泡的趟数
        boolean nextSort = true;
        for(int i = 0;i<= array.length-1&&nextSort;i++){
            //一趟冒泡的过程
            nextSort = false;
            for(int j=0;j< array.length-i-1;j++){
                if(array[j]>array[j+1]){
                    int tmp = array[j];
                    array[j] = array[j+1];
                    array[j+1] = tmp;
                    nextSort = true;
                }
            }
        }
    }

选择排序

思想

选择排序,选择序列中最小的元素与第一个元素进行交换。
它的工作原理是:第一次从待排序的数据元素中选出最小的一个元素,存放在序列的起始位置,然后再从剩余的未排序元素中寻找到最小元素,然后放到已排序的序列的末尾。以此类推,直到全部待排序的数据元素的个数为零。选择排序是不稳定的排序方法。
在这里插入图片描述

代码

代码如下

    public static void SelectSort(int[] array){
        if(array == null||array.length==0){
            return;
        }
        //时间复杂度O(n^2) 空间复杂度O(1)
        //稳定性:不稳定
        for(int i = 0;i< array.length;i++){
          //i表示待排序列的第一个值
            int minIndex = i;
            for(int j = i+1;j< array.length;j++){
                if(array[j]<array[minIndex]){
                    minIndex = j;
                }
            }
            //minIndex保存的最小元素下标
            if(minIndex!=i){
                int tmp = array[i];
                array[i] = array[minIndex];
                array[minIndex] = tmp;
            }
        }
    }

这里我们可以对算法进行优化,在每次将最小元素与第一位进行交换时,也将最大元素与最后一位进行交换。优化后的选择排序如下:

  public static void optimizedSelectSort(int[] array){
        if(array == null|| array.length == 0){
            return;
        }
        for(int i=0;i<array.length/2;i++){
            int minIndex = i;
            int maxIndex = i;
            for (int j=i+1;j<=array.length-1-i;j++){
                if(array[j]<array[minIndex]){
                    minIndex = j;
                    continue;
                }
                if(array[j]>array[maxIndex]){
                    maxIndex = j;
                }
            }
            //minIndex指向的最小值与第一个值进行交换
            int tmp = array[minIndex];
            array[minIndex] = array[i];
            array[i] = tmp;
            //
            if(maxIndex == i){
                maxIndex = minIndex;
            }

            //maxIndex指向的最大值与最后一个值交换
            tmp = array[maxIndex];
            array[maxIndex] = array[array.length-i-1];
            array[array.length-i-1]=tmp;
        }
    }

直接插入排序

思想

直接插入排序,每一趟将一个待排序的记录,按其关键字的大小插入到已经排好序的一组记录的适当位置上,直到所有待排序记录全部插入为止。我们可以类比打扑克,拿到一张牌,与手中牌从前往后进行比较找到比前大的,插入到他前面。
在这里插入图片描述

代码

代码如下:

    public static void insertSort(int[] array){
        if (array == null|| array.length==0){
            return;
        }
        //时间复杂度O(N^2) 空间复杂度O(1)
        //稳定性:稳定
        for (int i= 0;i< array.length;i++){
            int tmp = array[i];
            int j=0;
            for(j=0;j<=i-1;j++){
                if(array[j]>tmp){
                    break;
                }
            }
            //挪动j~array.length-1的牌往后一位
            for (int k = i-1;k>=j;k--){
                array[k+1]=array[k];
            }
            array[j] = tmp;
        }
    }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

降温vae+

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值