1、冒泡排序
- Bubble Sort,最简单的排序算法之一;
- 步骤:重复遍历数组,比较相邻元素,每一趟遍历都将此趟遇到的最大数放到数组后方;
- 趟数:n 个数据的数组,冒泡排序最多需要排序 n-1 趟才能完成排序(未优化的);
- 复杂度:平均时间复杂度为O(n^2);
- 稳定性:冒泡排序中,如果两个元素相等,是不会再交换的,所以冒泡排序是一种稳定排序算法。
2、Java代码
package Algorithm.Sort;
import java.text.SimpleDateFormat;
import java.util.Arrays;
import java.util.Date;
/**
* @author yhx
* @date 2020/09/28
*/
public class BobbleSort {
private static final int NUM = 100;
public static void main(String[] args) {
//定义待排序数组
int[] arr1 = {3, 9, -1, 10, -20};
int[] arr2 = {3, 9, -1, 10, -20};
int[] arr3 = new int[NUM];
for (int i = 0; i < NUM; i++) {
// .random()用于产生一个0到1的随机小数
arr3[i] = (int) ((Math.random() * 2 - 1) * NUM);
}
Bobble bobble = new Bobble();
// 基础步骤演示
System.out.println("冒泡排序基础步骤演示:");
bobble.bobbleProcess(arr1);
System.out.println();
// 整合优化后的算法
System.out.println("优化后的冒泡排序演示:");
bobble.bobble(arr2);
System.out.println("arr2[]冒泡排序后的结果为:" + Arrays.toString(arr2));
System.out.println();
// 用大量数据测试优化后的冒泡排序的排序速度
System.out.println("优化后的冒泡排序综合演示:");
// Date()函数用于标记时间
Date date1 = new Date();
// 时间标记精确到毫秒
SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss:SSS");
String date1Str = simpleDateFormat.format(date1);
System.out.println("arr3[]排序前的时间是:" + date1Str);
bobble.bobble(arr3);
Date date2 = new Date();
String date2Str = simpleDateFormat.format(date2);
System.out.println("arr3[]排序后的时间是:" + date2Str);
System.out.println("arr3[]冒泡排序后的结果为:" + Arrays.toString(arr3));
}
}
class Bobble {
/**
* 一步一步演示冒泡排序的步骤
*
* @param arr 待排序数组
*/
public void bobbleProcess(int[] arr) {
//第一趟排序:将最大的排在最后
//临时变量,用于交换
int temp;
for (int j = 0; j < arr.length - 1; j++) {
if (arr[j] > arr[j + 1]) {
temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
System.out.println("arr1[]第一趟冒泡排序:" + Arrays.toString(arr));
//第二趟排序:将第二大的排在倒数第二位
for (int j = 0; j < arr.length - 1 - 1; j++) {
if (arr[j] > arr[j + 1]) {
temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
System.out.println("arr1[]第二趟冒泡排序:" + Arrays.toString(arr));
//第三趟排序:将第三大的排在倒数第三位
for (int j = 0; j < arr.length - 1 - 1 - 1; j++) {
if (arr[j] > arr[j + 1]) {
temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
System.out.println("arr1[]第三趟冒泡排序:" + Arrays.toString(arr));
//第四趟排序:将第四大的排在倒数第四位
for (int j = 0; j < arr.length - -1 - 1 - 1 - 1; j++) {
if (arr[j] > arr[j + 1]) {
temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
System.out.println("arr1[]第四趟冒泡排序:" + Arrays.toString(arr));
}
/**
* 优化后的冒泡排序算法
*
* @param arr 待排序数组
*/
public void bobble(int[] arr) {
int temp;
// 定义一个标致变量
boolean flag = false;
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]) {
// 如果发生了位置变换,就将flag置为真
flag = true;
temp = arr[j];
arr[j] = arr[j + 1];
arr[j + 1] = temp;
}
}
// System.out.println("第" + (i + 1) + "趟:" + Arrays.toString(arr));
// 如果flag不为真,说明没有发生位置变换,也就说明当前数组已经有序,跳出循环
if (!flag) {
break;
}
// 如果flag为真,则将flag置为假,并继续下一轮的排序
else {
flag = false;
}
}
}
}
3、运行结果
冒泡排序基础步骤演示:
arr1[]第一趟冒泡排序:[3, -1, 9, -20, 10]
arr1[]第二趟冒泡排序:[-1, 3, -20, 9, 10]
arr1[]第三趟冒泡排序:[-1, -20, 3, 9, 10]
arr1[]第四趟冒泡排序:[-20, -1, 3, 9, 10]
优化后的冒泡排序演示:
arr2[]冒泡排序后的结果为:[-20, -1, 3, 9, 10]
优化后的冒泡排序综合演示:
arr3[]排序前的时间是:2020-09-29 09:10:29:218
arr3[]排序后的时间是:2020-09-29 09:10:29:246
arr3[]冒泡排序后的结果为:[-99, -97, -97, -97, -93, -90, -90, -87, -84, -80, -76, -76, -74, -74, -72, -70, -67, -63, -63, -61, -58, -56, -53, -51, -47, -47, -44, -43, -40, -38, -37, -36, -33, -33, -33, -32, -30, -29, -22, -20, -19, -18, -17, -16, -15, -13, -10, -8, -4, -4, -4, -1, 0, 0, 3, 7, 12, 15, 16, 16, 21, 21, 23, 23, 25, 27, 27, 31, 32, 33, 36, 41, 43, 44, 50, 53, 56, 56, 59, 60, 61, 63, 64, 68, 69, 71, 72, 73, 75, 75, 76, 77, 78, 79, 81, 84, 85, 87, 96, 97]