Java之冒泡排序
冒泡排序,从字面上理解,冒泡的话,可以想象鱼在水里吐泡泡,越接近水面的泡泡越大,越远离水面的泡泡越小,那么冒泡排序也就是一个种从小到大的排序。 冒泡排序的原理:比较相邻的两个数,将值大的交换值右端
思路
每次都比较相邻的两个数,在第一轮之后,最大的值就到了最右端,那么第二轮就可以少一次比较,因为在第一轮最大的值已经在右端,所以第二轮比较,最右端的数就不参与比较,也就少了1次比较; 到了第三轮,由于经过了第一轮和第二轮的比较,最大的值和第二大的值,都位于最右边,和右边起的第二个位置,那么第三轮就可以不用进行右边第一和第二个数的比较,所以在三轮的比较次数就少了2次; 后面的一次类推,最后的效果就是从左往右,从小到大。
案例
假如有一个数组int[] a = {2,3,4,1,5}
++++++++++++第 1 轮比较+++++++
第 1 次交换 2<3 不交换位置 2,3,4,1,5
第 2 次交换 3<4 不交换位置 2,3,4,1,5
第 3 次交换 4>1 交换位置 2,3,1,4,5
第 4 次交换 4<5 不交换位置 2,3,1,4,5
++++++++++++第 2 轮比较+++++++
第 1 次交换 2<3 不交换位置 2,3,1,4,5
第 2 次交换 3>1 交换位置 2,1,3,4,5
第 3 次交换 3<4 不交换位置 2,1,3,4,5
由于第一轮比较已将最大值放置最右边,所有不用进行第 4 个和第 5 个数比较
++++++++++++第 3 轮比较+++++++
第 1 次交换 2>1 交换位置 1,2,3,4,5
第 2 次交换 2<3 不交换位置 1,2,3,4,5
同上
++++++++++++第 4 轮比较+++++++
第 1 次交换 1<2 不交换位置 1,2 ,3,4,5
同上
++++++++++++比较结束+++++++
OK,到了这里,冒泡排序完成了,由之前的2,3,4,1,5换成了1,2,3,4,5
规律
我们进行了一共 4 轮的交换,如果把数组的长度看做 n 那么,我们一共需要进行 n-1 轮交换; 在每一轮我们都进行了不同次数的排序,同样把把数组长度看成是 n ,把轮数看成是 i ,那么在每一轮中,我们一共需要进行 n-i 次交换位置
代码实现
根据上面的规律,我们可以写两个for循环来说实现,一个循环来实现轮数 n-1 的规律,另一个循环来实现 n-m 的规律
n-1
定义一个变量 i ,i用来控制循环论述,所以初始值为1,那么每次循环都进行i++,且for循环条较为i<数组长度,也就实现了 n-1 规律
1 for(int i=1; i<a.length; i++)
n-i
定义一个变量 j ,用来控制每轮循环中的次数,那么每次循环都进行 j++ ,且for循环条件为 j<数组长度-i ,也就实现了n-1规律
for(int j=1;j<a.length-i;j++)
循环代码
因为数组的标是从0开始的,所以我们在上面两个for循环将 i 和 j 都定义成 0,那么在交换for循环条件那么相应的 -1 即可。
1 for(int i=0;i<a.length-1;i++){ 2 for(int j=0;j<a.length-i-1;j++){ 3 //交换位置代码 4 } 5 }
交换位置
定义一个中间变量用来存放临时的交换值:
if(a[j]>a[j+1])
最终实现
1 public class MaoPao { 2 public static void main(String[] args) { 3 4 int[] a = {2,3,4,1,5}; 5 int b = 0; 6 System.out.println("原始数组"); 7 for (int i : a) { 8 System.out.print(i+", "); 9 } 10 for (int i = 0; i < a.length-1; i++) { 11 for (int j = 0; j < a.length-i-1; j++) { 12 if(a[j]>a[j+1]){ 13 b = a[j+1]; 14 a[j+1] = a[j]; 15 a[j] = b; 16 } 17 } 18 } 19 System.out.println(); 20 System.out.println("冒泡排序之后"); 21 for (int i : a) { 22 System.out.print(i+", "); 23 } 24 25 } 26 }