排序算法之冒泡排序,通俗易懂,简单明了

一.什么是冒泡排序算法?

    简单来说,就是将待排序的数据像水底冒泡一样,水泡从小逐渐变大,就像是有序【升序】的一样。冒泡排序原理与其非常相似,拿升序【数据从小到大】排列来说,把每个数据都比作一个气泡【有大有小】,一次冒出一个最大的气泡,直到将所有气泡全部冒完数据便是有序了。

二.冒泡排序(Bubble Sort)的基本思想

   通过对待排序数据从前往后【从下标较小的元素开始】,依次比较相邻元素的值,假设要求数据按照升序排列,若发现前一个数据大于后一个,则将它们交换位置,使较大的元素逐渐从前向后移,就想水中的气泡一样逐渐向上冒。

三.冒泡排序的思路分析
   假设现在有一个数组arr,元素个数为n个,对数组arr元素进行升序排列

 1.一共冒泡n - 1次,也就是排序n-1趟

     解释:比如有5个数据待排序,一趟排出1个最大值,排4趟就是4个,此时剩下的一个自然就是最小的,就不要进行后续排序了。

 2.每排序一趟获得一个最大值,下一趟排序该最大值不参与

 3.每趟需要比较【相邻元素比较】的次数都比上一趟少1次

   解释:因为上一趟已经排出了1个最大值【不参与此趟比较】,所以此轮待排序的数据少1个,自然就要少比较1次。

冒泡排序步骤图解:

 

代码实现:

//冒泡排序
public void bubbleSort(int[] arr){
    //嵌套for循环,外层循环表示趟数,内层循环表示每一趟需要比较的次数
    for (int i = 0;i < arr.length - 1;i++){
        //每趟比较次数递减1,而i刚好符合条件,所以-i
        for (int j = 0;j < arr.length - i - 1;j++){
            if (arr[j] > arr[j+1]){//比较前一项比后一项大,就交换
                int temp = arr[j];
                arr[j] = arr[j+1];
                arr[j+1] = temp;
            }
        }
    }
}

三.时间复杂度

   因为有嵌套for循环,所以冒泡排序的时间复杂度为O(n^2)

四.冒泡排序的优化

  假设有一个数组arr = {6,1,2,3,4,5},现在使用冒泡排线对该数组进行升序排序,我们不难发现,只需要排序1趟该数组就有序了,那么后续几趟比较就是没有意义的,那么当某一趟数据已经有序了之后如何及时的终止排序呢?

  我们可以在每趟排序前设置一个布尔类型的flag标志变量,初始化为true:

 boolean flag = true;

 在交换的代码中,我们加上flag = false这行代码,就像这样:

if (arr[j] > arr[j+1]){//前一项比后一项大,就交换
    int temp = arr[j];
    arr[j] = arr[j+1];
    arr[j+1] = temp;
    flag = false;
}

 如果一趟比较下来,没有进行交换的话,flag也不会被更新为false,说明此时数据已经有序了,此时对flag进行判断,为true就退出循环。

if (flag)//true表示没有进行交换,则数组已经有序
    break;

优化过后的完整代码:

//冒泡排序【优化版】
public static void bubbleSort(int[] arr){
    //嵌套for循环,外层循环表示趟数,内层循环表示每一趟需要比较的次数
    for (int i = 0;i < arr.length - 1;i++){
         boolean flag = true;//判断是否在某一趟就有序的标志
        //每趟比较次数递减1,而i刚好符合条件,所以-i
        for (int j = 0;j < arr.length - i - 1;j++){
            if (arr[j] > arr[j+1]){//比较前一项比后一项大,就交换
                int temp = arr[j];
                arr[j] = arr[j+1];
                arr[j+1] = temp;
                //进行了交换,说明此趟数组还没有有序,所以更新flag的值为false
                flag = false;
            }
        }
        //排完一趟就对flag的值进行判断,为true表示已经有序,此时退出循环
        if (flag)
            break;
    }
}

 

  • 13
    点赞
  • 29
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 4
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

Ocean&21

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

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

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

打赏作者

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

抵扣说明:

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

余额充值