查找元素索引地位
根本查找
依据数组元素找出该元素第一次在数组中呈现的索引
public class TestArray1 { public static void main(String[] args) { //定义一个数组 int[] arr={10,20,70,10,90,100,1,2}; //依据元素查找出该元素在数组中第一次呈现的索引 int index=getIndexByEle(arr,2); System.out.println("该元素第一次在数组中呈现的索引是:"+index); } private static int getIndexByEle(int[] arr, int ele) { //遍历数组,去查找 for (int i = 0; i < arr.length; i++) { if (ele==arr[i]){ return i; } } return -1;//如果咱们没有找到这个元素那么就返回-1 }}
案例中查找元素2的索引,索引为7;
运行后返回后果正确:
二分查找
应用二分查找查找出该元素在数组中第一次呈现的索引
- 前提:该数组的元素必须有序
- 思维:每一次都查找两头的元素,比拟大小就能缩小一半的元素
具体代码实现:
public class TestArray2 { public static void main(String[] args) { //二分查找:前提是数组元素必须有序 int[] arr={10,20,30,40,50,60,70,80,90}; int index=getIndexByEle(arr,40); System.out.println("该元素的索引是:"+index); } private static int getIndexByEle(int[] arr, int ele) { //定义最小索引,两头索引,最大索引 int minIndex=0; int maxIndex=arr.length-1; int centerIndex=(minIndex+maxIndex)/2; while (minIndex<=maxIndex){ //如果需查找元素等于两头索引所对应元素,返回两头元素,示意找到 if (ele==arr[centerIndex]){ return centerIndex; } //如果需查找元素大于两头索引所对应元素,挪动最小索引至两头索引处 else if (ele>arr[centerIndex]){ minIndex=centerIndex+1; } //如果需查找元素小于两头索引所对应元素,挪动最大索引至两头索引处 else if (ele<arr[centerIndex]){ maxIndex=centerIndex-1; } //从新计算两头索索引 centerIndex=(minIndex+maxIndex)/2; } return -1;//如果没有找到,就返回-1 }}
案例中查找元素为40,索引为3;
运行后返回后果正确:
八大排序办法
冒泡排序
原理:数组元素两两比拟,替换地位,大元素往后放,通过一轮比拟后,最大的元素,就会被排到数组的最初
- 图解:
代码局部:
先进行第一轮排序,看看成果:
public class ArraySort1 { public static void main(String[] args) { //原理:数组元素两两比拟,后面元素大于前面元素则替换,否则不替换,每通过一轮,最大的元素会排到最初 int[] arr={24,69,80,57,13}; //第一轮比拟,遍历数组 for (int i = 0; i < arr.length-1; i++) { //从从第0个元素开始,前一个元素与后一个元素比拟 if (arr[i]>arr[i+1]){ //满足条件则替换地位,利用temp两头变量存放元素 int temp=arr[i]; arr[i]=arr[i+1]; arr[i+1]=temp; } } //输入数组 System.out.println(Arrays.toString(arr)); }}
上面进行多轮排序:
代码局部
笨办法:屡次for循环,比拟繁琐,反复循环,语句没养分,看看就好,次要是得能想到,为嵌套循环做筹备
public class ArraySort1 { public static void main(String[] args) { //原理:数组元素两两比拟,后面元素大于前面元素则替换,否则不替换,每通过一轮,最大的元素会排到最初 int[] arr={24,69,80,57,13}; //第一轮比拟,遍历数组 for (int i = 0; i < arr.length-1; i++) { //从从第0个元素开始,前一个元素与后一个元素比拟 if (arr[i]>arr[i+1]){ //满足条件则替换地位,利用temp两头变量存放元素 int temp=arr[i]; arr[i]=arr[i+1]; arr[i+1]=temp; } } //输入数组 System.out.println(Arrays.toString(arr)); //第二轮比拟,遍历数组 for (int i = 0; i < arr.length-1-1; i++) { if (arr[i]>arr[i+1]){ int temp=arr[i]; arr[i]=arr[i+1]; arr[i+1]=temp; } } //输入数组 System.out.println(Arrays.toString(arr)); //第三轮比拟,遍历数组 for (int i = 0; i < arr.length-1-1-1; i++) { if (arr[i]>arr[i+1]){ int temp=arr[i]; arr[i]=arr[i+1]; arr[i+1]=temp; } } //输入数组 System.out.println(Arrays.toString(arr)); //第四轮比拟,遍历数组 for (int i = 0; i < arr.length-1-1-1-1; i++) { if (arr[i]>arr[i+1]){ int temp=arr[i]; arr[i]=arr[i+1]; arr[i+1]=temp; } } //输入数组 System.out.println(Arrays.toString(arr)); }}
应用嵌套循环(语句精简,没有废话):
public class ArraySort1 { public static void main(String[] args) { //原理:数组元素两两比拟,后面元素大于前面元素则替换,否则不替换,每通过一轮,最大的元素会排到最初 int[] arr={24,69,80,57,13}; //嵌套for循环,外层循环轮数,内层对每一轮内元素进行比拟 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 temp=arr[j]; arr[j]=arr[j+1]; arr[j+1]=temp; } } } System.out.println(Arrays.toString(arr));}
冒泡排序就介绍到这里~~~
抉择排序
原理:从0索引处开始,顺次和前面的元素进行比拟,小的元素往前放,通过一轮比拟后,最小的元素就会呈现在最小索引处
图解:
代码局部:多轮排序(优化前)
public class ArraySort2 { public static void main(String[] args) { //原理:从0索引处开始,顺次个前面的元素进行比拟,小的元素往前放,通过一轮比拟,最小的元素就呈现在最小索引处 int[] arr={24,69,80,57,13}; //第一轮比拟,从0索引处开始比 int index=0; for (int i = 1; i < arr.length; i++) { if (arr[index]>arr[i]){ int temp=arr[index]; arr[index]=arr[i]; arr[i]=temp; } } System.out.println(Arrays.toString(arr)); //第二轮 index=1; for (int i = 1+index; i < arr.length; i++) { if (arr[index]>arr[i]){ int temp=arr[index]; arr[index]=arr[i]; arr[i]=temp; } } System.out.println(Arrays.toString(arr)); //第三轮 index=2; for (int i = 1+index; i < arr.length; i++) { if (arr[index]>arr[i]){ int temp=arr[index]; arr[index]=arr[i]; arr[i]=temp; } } System.out.println(Arrays.toString(arr)); //第四轮 index=3; for (int i = 1+index; i < arr.length; i++) { if (arr[index]>arr[i]){ int temp=arr[index]; arr[index]=arr[i]; arr[i]=temp; } } System.out.println(Arrays.toString(arr)); }}
优化代码:嵌套循环:
public class ArraySort2 { public static void main(String[] args) { //原理:从0索引处开始,顺次个前面的元素进行比拟,小的元素往前放,通过一轮比拟,最小的元素就呈现在最小索引处 int[] arr={24,69,80,57,13}; //第一轮比拟,从0索引处开始比 for (int index = 0; index < arr.length-1; index++) { for (int i = 1+index; i < arr.length; i++) { if (arr[index]>arr[i]){ int temp=arr[index]; arr[index]=arr[i]; arr[i]=temp; } } } System.out.println(Arrays.toString(arr));}
抉择排序就介绍到这里~~~
间接插入排序
原理:从1索引处开始,将前面的元素与前一位比,小于前一位则替换,再与前一位比,如果小于再替换,如此循环,插入之前的有序列表中使之仍放弃有序
(办法1):代码实现:
public class ArraySort3 { public static void main(String[] args) { //间接插入排序:从1索引处开始,将前面的元素,插入之前的有序列表中使之仍放弃有序 int[] arr={3,2,1,0,10,20,30,7,8}; //外层循环定义轮次 for (int i = 1; i < arr.length; i++) { //内层循环进行比拟插入 int j=i; while (j>0 && arr[j]<arr[j-1]){ int temp=arr[j]; arr[j]=arr[j-1]; arr[j-1]=temp; j--; } } System.out.println(Arrays.toString(arr)); }}
(办法2)代码实现:
public class ArraySort3 { public static void main(String[] args) { //间接插入排序:从1索引处开始,将前面的元素,插入之前的有序列表中使之仍放弃有序 int[] arr={3,2,1,0,10,20,30,7,8}; //外层循环定义轮次 for (int i = 0; i < arr.length; i++) { for (int j = i; j >0 ; j--) { if (arr[j]<arr[j-1]){ int temp=arr[j]; arr[j]=arr[j-1]; arr[j-1]=temp; } } } System.out.println(Arrays.toString(arr));}
因为很多中央须要应用前后元素值替换,因而封装成一个办法:代码如下:
public static void swapValue(int[] arr,int i,int j){ int temp=arr[i]; arr[i]=arr[j]; arr[j]=temp; }
应用本人封装的办法:
for (int i = 0; i < arr.length; i++) { for (int j = i; j >0 ; j--) { if (arr[j]<arr[j-1]){ /* int temp=arr[j]; arr[j]=arr[j-1]; arr[j-1]=temp; */ //间接调用替换办法,封装思维 swapValue(arr,j,j-1); } } }
间接插入排序就介绍到这里~~~
希尔排序
希尔排序又称放大增量排序
- 根本思维:先将原表按增量ht分组;每个子文件依照直接插入法排序。同样,用下一个增量ht/2将文件再分为自问见,在直接插入法排序。直到ht=1时整个文件排好序。
- 要害:抉择适合的增量。
- 希尔排序算法9-3:能够通过三重循环来实现。
图示:
**将数组按步长为5的距离两两分为一组,每组两个元素进行比拟大小,小的搁置于后面,大的搁置于前面;
由此排序一次后,大抵能够将整个数组中较小的元素放在后面,较大的放在前面。**
上面数组长度为8,第一次距离取4,第二次距离取2,第三次距离取1,具体实现见下图:
代码实现(应用克努特序列,正当抉择增量):
public class ArraySort4 { public static void main(String[] args) { //希尔排序,对插入排序的优化,核心思想就是正当的选取增量,通过一轮排序后,就会让序列大抵有序 //而后一直的放大增量,进行插入排序,直到增量为1整个排序完结 //间接插入排序,其实就是增量为1的希尔排序 int[] arr={46,55,13,43,17,94,5,70,11,25,110,234,1,3,66}; shellSort(arr); System.out.println(Arrays.toString(arr)); } private static void shellSort(int[] arr) { //定义一个增量 /* //第一轮 int h=4; for (int i = h; i < arr.length; i++) { for (int j = i; j > h-1 ; j-=h) { if (arr[j]<arr[j-h]){ swapValue(arr,j,j-h); } } } //第二轮 h=2; for (int i = h; i < arr.length; i++) { for (int j = i; j > h-1 ; j-=h) { if (arr[j]<arr[j-h]){ swapValue(arr,j,j-h); } } } //第三轮 h=1; for (int i = h; i < arr.length; i++) { for (int j = i; j > h-1 ; j-=h) { if (arr[j]<arr[j-h]){ swapValue(arr,j,j-h); } } } */ //希尔排序外围代码 //希尔排序的思维,正当的选取增量 //第一次增量能够选取数组长度的一半,而后一直的减半 /*for (int h = arr.length / 2; h > 0; h /= 2) { for (int i = h; i < arr.length; i++) { for (int j = i; j > h - 1; j -= h) { if (arr[j] < arr[j - h]) { swapValue(arr, j, j - h); } } } }*/ //增量的选取抉择数组长度的一半,还不是很正当,咱们能够应用一种序列,叫做克努特序列 //int h = 1; //h = h * 3 + 1; //1,4,13,40,121,364 //依据克努特序列选取咱们的第一次增量 int jiange = 1; while (jiange <= arr.length / 3) { jiange = jiange * 3 + 1; } for (int h = jiange; h > 0; h = (h - 1) / 3) { for (int i = h; i < arr.length; i++) { for (int j = i; j > h - 1; j -= h) { if (arr[j] < arr[j - h]) { swapValue(arr, j, j - h); } } } } } //封装元素替换办法 public static void swapValue(int[] arr,int i,int j){ int temp=arr[i]; arr[i]=arr[j]; arr[j]=temp; }}
希尔排序就介绍到这里~~~
疾速排序
原理:分治法:比大小,再分区
- 从数组中取出一个数,作为基准数
- 分区:将比这个数大或等于的书全放到他的左边,小于他的数全放到他的右边。
- 再对左右区间反复第二步,直到各区间只有一个数。
实现思路
- 将基准数挖出造成第一个坑
- 由后向前找比它小的数,找到后挖出此数填到前一个坑中
- 由前向后找比它大或等于的数,找到后也挖出此数填到前一个坑中。
- 再反复执行上述两步骤
代码实现:
public class ArraySort5 { public static void main(String[] args) { //定义一个数组 int[] arr={10,3,34,45,11,35,255,4,-1,-9,79,123}; quickSort(arr,0,arr.length-1); System.out.println(Arrays.toString(arr)); } //疾速排序 public static void quickSort(int[] arr,int start,int end) { //找出分左右两区的索引地位,而后对左右两区进行递归调用 if (start<end){ int index=getIndex(arr,start,end); quickSort(arr,start,index-1); quickSort(arr,index+1,end); } } //将基准数挖出造成第一个坑 //由后向前找比它小的数,找到后挖出此数填到前一个坑中 //由前向后找比它大或等于的数,找到后也挖出此数填到前一个坑中。 //再反复执行上述两步骤 private static int getIndex(int[] arr, int start, int end) { int i=start; int j=end; int x=arr[i]; while (i<j){ //由后向前找比它小的数,找到后挖出此数填到前一个坑中 while (i<j&&arr[j]>=x){ j--; } if (i<j){ arr[i]=arr[j]; i++; } //由前向后找比它大或等于的数,找到后也挖出此数填到前一个坑中。 while (i<j&&arr[i]<x){ i++; } if (i<j){ arr[j]=arr[i]; j--; } } arr[i]=x;//把基准数填到最初一个坑 return i; }}
疾速排序就介绍到这里~~~
归并排序
归并排序(Merge Sort)就是利用归并的思维实现排序的办法
原理:假如初始序列有N个记录,则能够看成是N个有序的子序列,每个子序列的长度为1,而后两两归并,失去N/2个长度为2或1的有序子序列,再两两归并。。。如此反复,直至失去一个长度为N的有序序列为止,这种排序办法称为2路归并排序
代码实现:
public class ArraySort6 { public static void main(String[] args) { //原始待排序数组 int[] arr={10,23,1,43,0,-3,1121,343,44,11,56,78,3,-1}; //咱们先给一个左右两边是有序的一个数组,先来进行归并操作 //int[] arr={4,5,7,8,1,2,3,6}; //拆分 chaifen(arr,0,arr.length-1); //归并 guiBing(arr,0,3,arr.length-1); //输入原数组 System.out.println(Arrays.toString(arr)); } private static void chaifen(int[] arr, int startIndex, int endIndex) { //计算两头索引 int centerIndex=(startIndex+endIndex)/2; if (startIndex<endIndex){ chaifen(arr,startIndex,centerIndex); chaifen(arr,centerIndex+1,endIndex); guiBing(arr,startIndex,centerIndex,endIndex); } } private static void guiBing(int[] arr, int startIndex, int centerIndex, int enIndex) { //定义一个长期数组 int[] tempArr=new int[enIndex-startIndex+1]; //定义右边数组的起始索引 int i=startIndex; //定义左边数组的起始索引 int j=centerIndex+1; //定义长期数组的起始索引 int index=0; while (i<=centerIndex && j<=enIndex){ if (arr[i]<=arr[j]){ tempArr[index]=arr[i]; i++; }else{ tempArr[index]=arr[j]; j++; } index++; } //解决残余元素 while (i<=centerIndex){ tempArr[index]=arr[i]; i++; index++; } while (j<=enIndex){ tempArr[index]=arr[j]; j++; index++; } //将长期数组中的元素取到原数组中 for (int k = 0; k < tempArr.length; k++) { arr[k+startIndex]=tempArr[k]; } }}
归并排序就介绍到这里~~~
基数排序
基数排序不同于之前的各类排序
后面的排序或多或少通过应用比拟和挪动记录来实现排序
而基数排序的实现不须要进行对关键字的比拟,只须要对关键字进行“调配”与“收集”两种操作即可实现
上面通过图来解释:
第一次排序:依照个位进行分组
分组后后果:
再将元素逐个取出:
第二次排序:依据十位上的数进行排序
再顺次将元素取出:
第三轮排序:依据百位上的数进行排序
最初将所有元素取出:
代码实现:
public class ArraySort7 { public static void main(String[] args) { //基数排序:通过调配再收集的形式进行排序 int[] arr={2,0,1,5,21,31,224,355,22,41,67,23,444,789,12,55,34,75}; //确定排序轮次 //获取数组中的最大值 int max=getMax(arr); //基数排序 sortArray(arr); //输入排序后的数组 System.out.println(Arrays.toString(arr)); } private static void sortArray(int[] arr) { //定义二维数组,放10个桶 int[][] tempArr=new int[10][arr.length]; //定义统计数组 int[] counts=new int[10]; int max=getMax(arr); int len=String.valueOf(max).length(); //循环轮次 for (int i = 0,n=1; i < len; i++,n*=10) { for (int j = 0; j < arr.length; j++) { //获取每个位上的数字 int ys=arr[j]/n%10; tempArr[ys][counts[ys]++]=arr[j]; } //取出桶中的元素 int index=0; for (int k = 0; k < counts.length; k++) { if (counts[k]!=0){ for (int h = 0; h < counts[k]; h++) { //从桶中取出元素放回原数组 arr[index]=tempArr[k][h]; index++; } counts[k]=0;//革除上一次统计的个数 } } } } private static int getMax(int[] arr) { int max=arr[0]; for (int i = 0; i < arr.length; i++) { if (arr[i]>max){ max=arr[i]; } } return max; }}
基数排序就介绍到这里~~~
堆排序
堆排序是利用堆这种数据结构而设计的一种排序算法,堆排序是一种抉择排序
- 将待排序序列结构成一个大顶堆,此时,整个序列的最大值就是堆顶的根节点。
- 将其与开端元素进行替换,此时开端就为最大值
- 而后将残余n-1个元素从新结构成一个堆,这样就会失去n个元素的次小值
- 如此重复的执行,便能失去一个有序序列了
代码实现:
public class ArraySort8 { public static void main(String[] args) { //定义一个数组 int[] arr={1,0,6,7,2,3,4,5,8,9,10,52,12,33}; //调整成大顶堆的办法 //定义开始调整的地位 int startIndex=(arr.length-1)/2; //循环开始调 for (int i = startIndex; i >=0 ; i--) { toMaxHeap(arr,arr.length,i); } //System.out.println(Arrays.toString(arr)); //通过下面的操作后,曾经把数组变成一个大顶堆,把根元素和最初一个元素进行调换 for (int i = arr.length-1; i >0; i--) { //进行调换 int temp=arr[0]; arr[0]=arr[i]; arr[i]=temp; //换完之后,咱们再把残余元素调成大顶堆 toMaxHeap(arr,i,0); } System.out.println(Arrays.toString(arr)); } /** * * @param arr 要排序的数组 * @param size 调整的元素个数 * @param index 从哪里开始调整 */ private static void toMaxHeap(int[] arr, int size, int index) { //获取左右字节的索引 int leftNodeIndex=index*2+1; int rightNodeIndex=index*2+2; //查找最大节点所对应的索引 int maxIndex=index; if (leftNodeIndex<size && arr[leftNodeIndex]>arr[maxIndex]){ maxIndex=leftNodeIndex; } if(rightNodeIndex<size && arr[rightNodeIndex]>arr[maxIndex]){ maxIndex=rightNodeIndex; } //咱们来调换地位 if(maxIndex!=index){ int t=arr[maxIndex]; arr[maxIndex]=arr[index]; arr[index]=t; //调换完之后,可能会影响到上面的子树,不是大顶堆,咱们还须要再次调换 toMaxHeap(arr,size,maxIndex); } }}
堆排序就介绍到这里~~~
最初
感激你看到这里,文章有什么有余还请斧正,感觉文章对你有帮忙的话记得给我点个赞,每天都会分享java相干技术文章或行业资讯,欢送大家关注和转发文章!