这篇博客的大纲:
1.冒泡排序
2.选择排序
3.插入排序
4.希尔排序
5.归并排序
6.快速排序
7.堆排序
8.计数排序
9.桶排序
10.基数排序
1.冒泡排序
思想:对待排序的序列,从前往后,依次比较相邻元素的值,若发现逆序则交换,使较大的元素逐渐从前移向后部
优化点:因为排序的过程中,各元素不断接近自己的位置,如果一躺比较下来,没有进行交换,就说明序列有序,可以用一个flag标识,减少没必要的排序
图解:
原始数组: 3 9 -1 10 20第一趟排序 (依次比较)
3 9 -1 10 20 (3和9比较,不用交换)
3 -1 9 10 20 (-1和9比较,交换)
3 -1 9 10 20 (9和10比较,不用交换)
3 -1 9 10 20 (10和20比较,不用交换 确定20是最大的)
第二趟排序 3 -1 9 10 20-1 3 9 10 20 (3和-1比较,交换)
-1 3 9 10 20 (3和9比较,不用交换)
-1 3 9 10 20 (9和10比较,不用交换,确定10是第二大)
第三趟排序 -1 3 9 10 20-1 3 9 10 20 (-1和3比较,不用交换)
-1 3 9 10 20 (3和9比较,不用交换,确定9第三大)
第四趟排序 -1 3 9 10 20-1 3 9 10 20 (-1 和3比较,不用交换,确定3第四大)
规律:
// 分析数据的特点 // 肯定要经历过数组长度-1趟的排序 // 每一趟的排序次数= 数组长度-属于第几趟 // 优化点:如果一趟比较下来,没有进行交换,就说明序列有序,因此可以在排序的过程中加一个flag标志判断是否进行过交换
分步代码演示:
import java.util.Arrays;
/**
* description: 思想:从下标较小的元素开始,依次比较相邻元素的值,若发现逆序,则交换,使较大的值从前移向后部
*
* @author carry.wu
* @version 1.0
* @date 2021/6/8 20:02
*/
public class BubbleSort {
public static void main(String[] args) {
int[] a = {3, 9, -1, 10, 20};
int temp = 0;
System.out.println("第一趟排序---------");
// 第一趟排序
for (int i =0; i<a.length-1; i++) {
if (a[i] > a[i+1]) {
temp = a[i];
a[i] = a[i+1];
a[i+1] = temp;
}
System.out.println(Arrays.toString(a));
}
System.out.println("第二趟排序---------");
for (int i =0; i<a.length-1-1; i++) {
if (a[i] > a[i+1]) {
temp = a[i];
a[i] = a[i+1];
a[i+1] = temp;
}
System.out.println(Arrays.toString(a));
}
System.out.println("第三趟排序---------");
for (int i =0; i<a.length-1-1-1; i++) {
if (a[i] > a[i+1]) {
temp = a[i];
a[i] = a[i+1];
a[i+1] = temp;
}
System.out.println(Arrays.toString(a));
}
System.out.println("第四趟排序---------");
for (int i =0; i<a.length-1-1-1-1; i++) {
if (a[i] > a[i+1]) {
temp = a[i];
a[i] = a[i+1];
a[i+1] = temp;
}
System.out.println(Arrays.toString(a));
}
// 分析数据的特点
// 肯定要经历过数组长度-1趟的排序
// 每一趟的排序次数= 数组长度-属于第几趟
// 优化点:如果一趟比较下来,没有进行交换,就说明序列有序,因此可以在排序的过程中加一个flag标志判断是否进行过交换
}
}
完整代码:
import java.util.Arrays;
/**
* description: 思想:从下标较小的元素开始,依次比较相邻元素的值,若发现逆序,则交换,使较大的值从前移向后部
*
* @author carry.wu
* @version 1.0
* @date 2021/6/8 20:02
*/
public class BubbleSort2 {
public static void main(String[] args) {
int[] a = {3, 9, -1, 10,20};
int temp = 0;
boolean flag = false;
// 第一趟排序
for (int i = 0; i < a.length - 1; i++) {
System.out.println("第" + (i + 1) + "趟排序");
for (int j = 0; j < a.length - 1 - i; j++) {
if (a[j] > a[j + 1]) {
temp = a[j];
a[j] = a[j + 1];
a[j + 1] = temp;
flag = true;
}
System.out.println(Arrays.toString(a));
}
if (!flag) {
break;
} else {
flag = false;
}
}
}
}
2.选择排序
思想:第一次从arr[0]-arr[n-1]中取最小值,与a[0]交换,第二次从arr[1]-arr[n-1]中取最小值,与a[1]交换以此类推:第i次,从arr[i-1]--arr[n-1]中取最小值
图解:
原始数组: 101 34 119 1
第一轮排序:
1 34 119 101 (确定1第一小)第二轮排序:
1 34 119 101 (确定34第二小)第三轮排序
1 34 101 119 (确定101第三小)规律:
1.选择排序共有数组长度-1轮大排序
2.每一轮排序,又是一轮循环
2.1 先假定当前这个数是最小的数
2.2 拿着这个数和后面的每个数进行比较,如果发现有比当前数更小的数,就重新确定最小的数并得到下标
2.3当遍历到数组的最后时,就得到本轮最小数和下标
2.4交换
分步代码实现:
import java.util.Arrays;
import java.util.concurrent.ConcurrentHashMap;
/**
* description: 选择排序:第一次从arr[0]-arr[n-1]中取最小值,与a[0]交换,第二次从arr[1]-arr[n-1]中取最小值,与a[1]交换以此类推
*
* @author carry.wu
* @version 1.0
* @date 2021/6/9 19:56
*/
public class SelectSort {
public static void main(String[] args) {
int[] arr = {101, 34, 119, 1};
int minIndex = 0;
int min = arr[0];
for (int i = 1; i < arr.length; i++) {
if (min > arr[i]) {
// 假定的最小值不是最小值
min = arr[i]; // 重置min
minIndex = i; // 重置minIndex
}
}
// 将最小值,放在arr[0],即交换
if (minIndex != 0) {
arr[minIndex] = arr[0];
arr[0] =min;
}
System.out.println("第一次排序");
System.out.println(Arrays.toString(arr));
minIndex = 1;
min = arr[1];
for (int i = 1+1; i < arr.length; i++) {
if (min > arr[i]) {
// 假定的最小值不是最小值
min = arr[i]; // 重置min
minIndex = i; // 重置minIndex
}
}
// 将最小值,放在arr[1],即交换
if (minIndex != 1) {
arr[minIndex] = arr[1];
arr[1] =min;
}
System.out.println("第二次排序");
System.out.println(Arrays.toString(arr));
minIndex = 2;
min = arr[2];
for (int i = 1+1+1; i < arr.length; i++) {
if (min > arr[i]) {
// 假定的最小值不是最小值
min = arr[i]; // 重置min
minIndex = i; // 重置minIndex
}
}
// 将最小值,放在arr[2],即交换
if (minIndex != 2) {
arr[minIndex] = arr[2];
arr[2] =min;
}
System.out.println("第三次排序");
System.out.println(Arrays.toString(arr));
// 分析规律: 会进行数组长度-1次大循环,每个大循环里面又有数组长度-第几次循环-1
}
}
完全代码:
/**
* description: 选择排序:第一次从arr[0]-arr[n-1]中取最小值,与a[0]交换,第二次从arr[1]-arr[n-1]中取最小值,与a[1]交换以此类推
*
* @author carry.wu
* @version 1.0
* @date 2021/6/9 19:56
*/
public class SelectSort2 {
public static void main(String[] args) {
int[] arr = {101, 34, 119, 1};
// int[] arr = {101, 100, 99, 1};
for (int j = 0; j < arr.length-1; j++) {
int minIndex = j;
int min = arr[j];
for (int i = j+1; i < arr.length; i++) {
if (min > arr[i]) {
// 假定的最小值不是最小值
min = arr[i]; // 重置min
minIndex = i; // 重置minIndex
}
}
if (minIndex != j) {
arr[minIndex] = arr[j];
arr[j] = min;
}
System.out.println("第"+(j+1)+"次排序");
System.out.println(Arrays.toString(arr));
}
}
}