交换排序之冒泡排序
冒泡排序
温故而知新,可以为师已。O(∩_∩)O~
冒泡排序算法是通过多次比较和交换来实现排序的,其排序流程如下:
1.对数组中的各元素(N个),依次比较相邻的两个元素的大小。
2.如果前面的元素大于后面的元素,就交换这个两个元素。经过第一轮的多次比较排序后,最大的元素到达了它最后的位置。
3.再按同样的方法把剩下的元素逐个进行比较,最后就按从小到大的顺序把数组中的各元素排列好。
即:
第一趟:
第一个和第二个元素比较,第二个和第三个元素比较...直到第N-1个元素和第N个元素比较,此时最大的元素跑到了最后面。比较了N-1次。
第二趟:
第一个和第二个元素比较,第二个和第三个元素比较...直到第N-2个元素和第N-1个元素比较,此时第二大的元素跑到了最大的元素的前面。比。较了N-2次。
......
最后一趟:
第1个元素和第2个元素比较,比较1次,即完成了冒泡排序。
冒泡排序示意图如下:
可以总结出,总共比较了N-1次,换个角度想,每一趟比较都是把最大的一个元素挑出来放到后面(当然是除了之前已经被挑出来放到后面的元素),N-1趟就能排序完成。
这样子看来,冒泡排序是不是应该叫吹泡排序更好?大的泡泡依次被吹到了后面,小的泡泡在前面....
冒泡排序算法在对N个数据进行排序时,无论原数据是否有序,都需要进行N-1步的排序。
这个排序方法思路简单直观,但是缺点是效率不高。改进的方式是:若发现一趟排序过程中没有发生元素交换,冒泡排序算法就终止。
既然冒泡排序要排序N-1趟,每趟比较的次数从N-1开始递减,那么,可以考虑用for循环嵌套来完成冒泡排序。
原始的冒泡排序算法核心代码如下:
1 for(int i=0;i<arr.length-1;i++){//外层循环控制总共要循环arr.length-1趟 2 for(int j=0;j<arr.length-1-i;j++){//内层循环控制每一趟循环要比较多少次,随着趟数的递增,每一趟内需要比较的次数逐渐减少 3 if(arr[j]>arr[j+1]){//若前一个元素比临近的后一个元素大,就执行交换操作 4 int temp=arr[j]; 5 arr[j]=arr[j+1]; 6 arr[j+1]=temp; 7 } 8 } 9 }
写个小程序测试一下:
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
public class BubbleSortDemo{ public static void main(String args[]){ int[] arr={12,3,7,58,32,14,2}; Sort sort=new Sort(); sort.BubbleSort(arr); } } class Sort{ public void BubbleSort(int arr[]){ for(int i=0;i<arr.length-1;i++){ for(int j=0;j<arr.length-1-i;j++){ if(arr[j]>arr[j+1]){ int temp=arr[j]; arr[j]=arr[j+1]; arr[j+1]=temp; } } } for(int i=0;i<arr.length;i++){ System.out.print(arr[i]+" "); } } }
一开始在运行上面的程序的时候报错:“需要.class”,很费解,后来发现,原来是sort.BubbleSort(arr[]);中我多写了个“[]”,画蛇添足了。。。
下面是改进后的冒泡排序,其实打印arr数组的代码可以另外写一个方法,但我写在了BubbleSort()方法里面,所以就顺便使用了标签来跳出外层for循环,若不使用标签而直接使用return退出方法if(!flag){return;}则无法执行下面的打印数组的代码:
1 public class BubbleSortImprove{ 2 public static void main(String args[]){ 3 4 int[] arr={12,3,7,58,32,14,2,34,2145,35,356,1,0,-1,-199,-6,88}; 5 Sort sort=new Sort(); 6 sort.BubbleSort(arr); 7 } 8 } 9 10 class Sort{ 11 12 public void BubbleSort(int arr[]){ 13 boolean flag;//变量flag用来标记本趟排序是否有交换发生 14 label://标签 15 for(int i=0;i<arr.length-1;i++){ 16 flag=false; 17 for(int j=0;j<arr.length-1-i;j++){ 18 if(arr[j]>arr[j+1]){ 19 int temp=arr[j]; 20 arr[j]=arr[j+1]; 21 arr[j+1]=temp; 22 flag=true;//一趟排序里只要有交换发生,就将flag改为true 23 } 24 } 25 if(!flag){//如果一趟排序过程中没有发生元素交换,就证明序列已经有序,排序结束。 26 break label;//跳出外层的for循环 27 } 28 } 29 for(int i=0;i<arr.length;i++){ 30 System.out.print(arr[i]+" "); 31 } 32 } 33 }
好吧,冒泡排序就先总结到这里。加油!!!