查找算法
https://blog.csdn.net/yan8024/article/details/73118391
1. 二分法查找
实现查找指定数值在元素有序的数组中存储的位置(索引),返回该位置(索引)。
解题步骤:
1.定义3个用来记录索引值的变量,变量min记录当前范围最小索引值,初始值为0;变量max记录当前范围最大索引值,初始值为数组长度-1;变量mid记录当前当前范围最中间元素的索引值,初始值为(min+max) / 2
2.使用循环,判断当前范围下,最中间元素值与指定查找的数值是否相等
若相等,结束循环,返回当前范围最中间元素的索引值mid
若不相等,根据比较结果,缩小查询范围为上一次查询范围的一般
中间元素值 比 要查询的数值大,说明要查询的数值在当前范围的最小索引位置与中间索引位置之间,此时,更新查询范围为:
范围最大索引值 = 上一次中间索引位置 -1;
中间元素值 比 要查询的数值小,说明要查询的数值在当前范围的最大索引位置与中间索引位置之间,此时,更新查询范围为:
范围最小索引值 = 上一次中间索引位置 +1;
在新的查询范围中,更新中间元素值的位置,再次使用最中间元素值与指定查找的数值是否相等。
中间索引值 = (范围最小索引值 +范围最大索引值) / 2;
3.每次查询范围缩小一半后,使用if语句判断,查询范围是否小于0个元素,若小于0个元素,则说明指定数值没有查询到,返回索引值-1。
public int binarySearch(int num,int[] array){
int min = 0; // 最小标
int max = array.length-1; //最大标
int mid = 0; //中间标
while (min<max){
mid = (min + max) / 2;
if(num< array[mid]){
max = mid-1;
}else if(num > array[mid]){
min = mid+1;
}else{
return mid;
}
}
return -1;
}
2. 顺序查找
public int orderSearch(int num,int[] array){
for(int i= 0;i< array.length; i++){
if(num == array[i]){
return i;
}
}
return -1;
}
排序算法
https://blog.csdn.net/luo_boke/article/details/106762372
https://luoxiaohui.blog.csdn.net/article/details/83177401
1. 冒泡排序
1. 算法描述
- 比较相邻的元素。如果第一个比第二个大,就交换它们两个;
- 对每一对相邻元素作同样的工作,从开始第一对到结尾的最后一对,这样在最后的元素应该会是最大的数;
- 针对所有的元素重复以上的步骤,除了最后一个;
- 重复步骤1~3,直到排序完成。
public int[] 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 a=arr[j];
arr[j] = arr[j+1];
arr[j+1] = a;
}
}
}
return arr;
}
2. 选择排序
算法描述:
1. 从第一个元素开始,分别与后面的元素进行比较,找到最小的元素,并与第一个元素交换位置
2. 从第二个元素开始,分别与后面的元素进行比较,找到最小的元素,并与第二个元素交换位置
3. 以此类推,直到最后一个元素
public int[] selectSort(int[] arr){
for(int i=0; i< arr.length;i++){
int minIndex = i;
for( int j = 1; j < arr.length; j++){
if(arr[minIndex] > arr[j]){
minIndex = j;
}
}
int temp = arr[i];
arr[i] = arr[minIndex];
arr[minIndex] = temp;
}
return arr;
}
3. 插入排序
1、以数组的某一位作为分隔位,比如index=1,假设左面的都是有序的.
2、将index位的数据拿出来,放到临时变量里,这时index位置就空出来了.
3、从leftindex=index-1开始将左面的数据与当前index位的数据(即temp)进行比较,如果array[leftindex]>temp, 则将array[leftindex]后移一位,即array[leftindex+1]=array[leftindex],此时leftindex 就空出来了.
4、再用index-2(即leftindex=leftindex-1)位的数据和temp比,重复步骤3,直到找到<=temp的数据或者比到了最左面(说明temp最小),停止比较,将temp放在当前空的位置上.
5、index向后挪1,即index=index+1,temp=array[index],重复步骤2-4,直到index=array.length,排序结束,此时数组中的数据即为从小到大的顺序.
public int[] insertSort(int[] arr){
for(int i = 1; i < arr.length; i++){
int temp = arr[i];
int leftIndex = i-1;
while( leftIndex >= 0 && arr[leftIndex] > temp){
arr[leftIndex+1] = arr[leftIndex];
leftIndex--;
}
arr[leftIndex+1] = temp;
}
return arr;
}
4. 快速排序
基于分治的思想,是冒泡排序的改进型。
首先在数组中选择一个基准点(该基准点的选取可能影响快速排序的效率,后面讲解选取的方法),然后分别从数组的两端扫描数组,设两个指示标志(lo指向起始位置,hi指向末尾),首先从后半部分开始,如果发现有元素比该基准点的值小,就交换lo和hi位置的值,然后从前半部分开始扫描,发现有元素大于基准点的值,就交换lo和hi位置的值,如此往复循环,直到lo>=hi,然后把基准点的值放到hi这个位置。一次排序就完成了。以后采用递归的方式分别对前半部分和后半部分排序,当前半部分和后半部分均有序时该数组就自然有序了。
1. 当low=height时,此时排序结束,数组已经有序了
2. 获取基准数pivot索引,一般第一个基准索引为0
3. 计算出基准值得所以后,此时左边的数组都小于pivot,右边的数据都大于pivot
4. 采用归并递归的思想,循环执行第3步,直到low-=height,此时排序完成
private void quickSort(int[] arr, int low, int high) {
if (low < high) {
// 找寻基准数据的正确索引
int index = getPivotIndex(arr, low, high);
// 进行迭代对index之前和之后的数组进行相同的操作使整个数组变成有序
quickSort(arr, low, index - 1);
quickSort(arr, index + 1, high);
}
}/**
* 获取 排序索引
* 1.获取数组arr的第一个数为基准数pivot
* 2.当low<height时,先从右到左扫描,如果arr[height]>=pivot,height--;
* 如果arr[height]<pivot,它应该放在pivot左边,此时执行arr[low] = arr[high],结束从右到左的扫描
* 3.当low < high时,从右到左结束扫描后,开始从左到右的扫描。如果arr[low] <= pivot,low++继续扫描;
* 如果arr[low] > pivot,说明arr[low]应该放在pivot的右边,此时执行arr[high] = arr[low],从右到左扫描结束
* 4.while循环第一轮结束,如果low < high则继续执行2、3操作查找pivot的索引,此时查找的范围low~height已经缩小了
* 5.直到low =height,此时low或者height就是pivot的索引
*
* @param arr 源数组
* @param low 最低排序索引
* @param height 最高排序索引
* @return 基准值的索引位置
*/
private int getPivotIndex(int[] arr, int low, int height) {
// 基准数据
int pivot = arr[low];
while (low < height) {
// 当队尾的元素大于等于基准数据时,向前挪动high指针
while (low < height && arr[height] >= pivot) {
height--;
}
// 如果队尾元素小于tmp了,需要将其赋值给low
arr[low] = arr[height];
// 当队首元素小于等于tmp时,向前挪动low指针
while (low < height && arr[low] <= pivot) {
low++;
}
// 当队首元素大于tmp时,需要将其赋值给high
arr[height] = arr[low];
}
// 跳出循环时low和high相等,此时的low或high就是tmp的正确索引位置
// 由原理部分可以很清楚的知道low位置的值并不是tmp,所以需要将tmp赋值给arr[low]
arr[low] = pivot;
return low;
}