冒泡排序
思想
排序原理:
- 比较相邻的元素。如果前一个元素比后一个元素大,就交换这两个元素的位置。最终最后位置的元素就是最大值。
- 两个for循环,第一个for循环是比较的趟数,第二个for循环是每趟比较的次数。
- 第一个for循环的arr.length - 1是为了防止数组的越界,arr.length - 1- i中的-i是每次比较最大的都放在了后面的位置,后面的位置已经有序了,不需要比较,-i是减掉后面的位置
代码
package other.BubbleSort;
import java.util.Arrays;
public class BubbleSort {
public static void BubbleSort(int[] arr) {
for (int i = 0; i < arr.length - 1; i++) {//冒泡趟数
for (int j = 0; j < arr.length - i - 1; j++) {
if (arr[j + 1] < arr[j]) {//从大到小。如果是从小到大,if (arr[j + 1] > arr[j])
// temp = arr[j];
// arr[j] = arr[j + 1];
// arr[j + 1] = temp;
exchange(arr,j,j+1);
}
}
}
}
public static void exchange(int[] arr, int i, int j){
int temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
public static void main(String[] args) {
int arr[] = new int[]{3, 1, 5, 4, 2};
BubbleSort.BubbleSort(arr);
System.out.println(Arrays.toString(arr));
}
}
快速排序
快排思想
找基准,然后按照基准分成两部分。左边小,右边大。然后不断的递归。
快速排序,说白了就是给基准数据找其正确索引位置的过程.
如下图所示,假设最开始的基准数据为数组第一个元素23,则首先用一个临时变量去存储基准数据,即tmp=23;然后分别从数组的两端扫描数组,设两个指示标志:low指向起始位置,high指向末尾.
代码
package other.QSort;
public class QuickSort {
public static void main(String[] args) {
int[] arr = { 49, 38, 65, 97, 23, 22, 76, 1, 5, 8, 2, 0, -1, 22 };
quickSort(arr, 0, arr.length - 1);
System.out.println("排序后:");
for (int i : arr) {
System.out.print(i + " ");
}
}
private static void quickSort(int[] arr, int low, int high) {
if (low < high) {
// 找寻基准数据的正确索引
int index = getIndex(arr, low, high);
quickSort(arr, low, index - 1);
quickSort(arr, index + 1, high);
}
}
private static int getIndex(int[] arr, int low, int high) {
// 基准数据
int tmp = arr[low];
while (low < high) {
// 当队尾的元素大于等于基准数据时,向前挪动high指针
while (low < high && arr[high] >= tmp) {
high--;
}
// 如果队尾元素小于tmp了,需要将其赋值给low
arr[low] = arr[high];
// 当队首元素小于等于tmp时,向前挪动low指针
while (low < high && arr[low] <= tmp) {
low++;
}
// 当队首元素大于tmp时,需要将其赋值给high
arr[high] = arr[low];
}
// 跳出循环时low和high相等,此时的low或high就是tmp的正确索引位置
// 由原理部分可以很清楚的知道low位置的值并不是tmp,所以需要将tmp赋值给arr[low]
arr[low] = tmp;
return low; // 返回tmp的正确位置
}
}
二分查找
int search(int arr[], int size, int target) //nums是数组,size是数组的大小,target是需要查找的值
{
int left = 0;
int right = size - 1; // 定义了target在左闭右闭的区间内,[left, right]
while (left <= right) { //当left == right时,区间[left, right]仍然有效
int mid = left + ((right - left) / 2);//等同于 (left + right) / 2,防止溢出
if (arr[mid] > target) {
right = mid - 1; //target在左区间,所以[left, middle - 1]
} else if (arr[mid] < target) {
left = mid + 1; //target在右区间,所以[middle + 1, right]
} else { //既不在左边,也不在右边,那就是找到答案了
return mid;
}
}
//没有找到目标值
return -1;
}