Java常见算法_常见的查找算法和排序算法——简介及代码演示

        在本文中我将介绍Java中的常见算法,查找算法包括基本查找、二分查找、插值查找和分块查找。排序算法包括冒泡排序、选择排序、插入排序和快速排序

查找算法:

1.基本查找:
代码:
public class BasicSearchDemo {public static void main(String[] args) {int[] arr = {1,21,31,41,51,61,71,81};Scanner sc = new Scanner(System.in);String numStr = sc.nextLine();int num = Integer.parseInt(numStr);boolean result = basicSearch(arr, num);System.out.println(result);}//基本查找方法public static boolean basicSearch(int[] arr, int number) {for (int i = 0; i < arr.length; i++) {if(arr[i] == number) {return true;}}return false;}
}

这是简单的基本查找,通过遍历数组来查看元素是否存在

运行结果:

基本查找小练习:
代码(含题目要求):
public class BasicSearchTest {public static void main(String[] args) {/*练习1:需求:定义一个方法利用基本查找,查询某个元素在数组中的索引要求:不需要考虑数组中元素是否重复*//*练习2:需求:定义一个方法利用基本查找,查询某个元素在数组中的索引要求:需要考虑数组中元素有重复的可能性例如:{1,1,1,2,3,4,5,6,1}若查找1,则需要返回所有元素1的索引,即0,1,2,8*///生成一个数组int[] arr = {1,11,21,31,41,51,51,61,51,61};//键盘录入一个元素Scanner sc = new Scanner(System.in);System.out.println("请输入您要查找的元素:");String numStr = sc.nextLine();int num = Integer.parseInt(numStr);System.out.println(getIndex(arr, num));System.out.println(getAllIndex(arr, num));}//练习1public static int getIndex(int[] arr, int number) {for (int i = 0; i < arr.length; i++) {if(arr[i] == number) {return i;}}return -1;}//练习2public static ArrayList<Integer> getAllIndex(int[] arr, int number) {ArrayList<Integer> list = new ArrayList<>();for (int i = 0; i < arr.length; i++) {if(arr[i] == number) {list.add(i);}}return list;}
}
运行结果:

2.二分查找:

特点:

        二分查找的数据必须是按大小顺序排好的二分查找可以很大的提高查找效率
代码:
public class BinarySearchDemo1 {public static void main(String[] args) {//二分查找的数据必须是按大小顺序排好的//二分查找可以很大的提高查找效率//定义数组int[] arr = {1,21,31,41,51,61,71,81};//键盘录入一个要查找的元素System.out.println("输入要查找的元素:");Scanner sc = new Scanner(System.in);String numStr = sc.nextLine();int num = Integer.parseInt(numStr);System.out.println(binarySearch(arr, num));}//定义二分查找方法public static int binarySearch(int[] arr, int num) {//用min和max表示当前查找范围int min = 0;int max = arr.length - 1;while (true) {//这种情况说明元素不存在if(min > max) {return -1;}//定义中间指针int mid = (min + max) / 2;//进行判断if(arr[mid] < num) {//元素在右边min = mid + 1;} else if(arr[mid] > num) {//元素在左边max = mid - 1;} else {//找到了return mid;}}}
}
3.插值查找:

        改变mid位置时使用数学公式使其更靠近要查找的元素

特点:

        适用于数据分布较均匀的情况下
代码:
public class InterpolationSearch {public static void main(String[] args) {//适用于数据分布较均匀的情况下int[] arr = {1,2,3,5,6,8,9,10};System.out.println("请输入要查找的元素值:");Scanner sc = new Scanner(System.in);String numStr = sc.nextLine();int num = Integer.parseInt(numStr);int index = interpolationSearch(arr, num);System.out.println(index);}public static int interpolationSearch(int[] arr, int num) {//定义查找范围int min = 0;int max = arr.length - 1;while(true) {if(min > max) {return -1;}//mid = min + (key - arr[min]) / (arr[max] - arr[min]) * (max - min)int mid = min + (num - arr[min]) / (arr[max] - arr[min]) * (max - min);if(arr[mid] > num) {max = mid - 1;} else if(arr[mid] < num) {min = mid + 1;} else {return mid;}}}
}
4.分块查找:

        对数据先进行分块,通过先确定要查找的元素属于哪个块,再只需对那个块进行遍历

代码:
public class BlockSearch {public static void main(String[] args) {//注意分块的块数跟元素个数的开方差不多即可//前一块所有元素都小于后一块中的任意元素int[] arr = {16, 5, 9, 12, 21, 18,32, 23, 37, 26, 45, 34,50, 48, 61, 52, 73, 66};//分块Block b1 = new Block(21, 0, 5);Block b2 = new Block(45, 6, 11);Block b3 = new Block(73, 12, 17);//用数组存储Block[] blockArr = {b1,b2,b3};//输入要查找的元素Scanner sc = new Scanner(System.in);System.out.println("请输入要查找的元素");String numStr = sc.nextLine();int num = Integer.parseInt(numStr);int index = getIndex(arr, blockArr, num);System.out.println(index);}private static int getIndex(int[] arr, Block[] blockArr, int num) {int blockIndex = getBlock(blockArr, num);if(blockIndex == -1) {return -1;}//将范围缩小到这块的开始和结束索引int startIndex = blockArr[blockIndex].getStartIndex();int endIndex = blockArr[blockIndex].getEndIndex();//遍历for (int i = startIndex; i <= endIndex; i++) {if(arr[i] == num) {return i;}}return -1;}private static int getBlock(Block[] blockArr, int num) {for (int i = 0; i < blockArr.length; i++) {if(num < blockArr[i].getMax()) {return i;}}return -1;}}class Block {private int max;private int startIndex;private int endIndex;public Block() {}public Block(int max, int startIndex, int endIndex) {this.max = max;this.startIndex = startIndex;this.endIndex = endIndex;}/*** 获取* @return max*/public int getMax() {return max;}/*** 设置* @param max*/public void setMax(int max) {this.max = max;}/*** 获取* @return startIndex*/public int getStartIndex() {return startIndex;}/*** 设置* @param startIndex*/public void setStartIndex(int startIndex) {this.startIndex = startIndex;}/*** 获取* @return endIndex*/public int getEndIndex() {return endIndex;}/*** 设置* @param endIndex*/public void setEndIndex(int endIndex) {this.endIndex = endIndex;}public String toString() {return "Block{max = " + max + ", startIndex = " + startIndex + ", endIndex = " + endIndex + "}";}
}

排序算法:

1.冒泡排序:
特点:
        相邻的元素两两比较,大的放右边,小的放左边(从小到大情况)第一轮比较完毕之后,最大值就已经确定,第二轮可以少循环一次,后面以此类推如果数组中有n个数据,那总共执行n-1轮代码就可以
代码:
public class BubbleSort {public static void main(String[] args) {//相邻的元素两两比较,大的放右边,小的放左边(从小到大情况)//第一轮比较完毕之后,最大值就已经确定,第二轮可以少循环一次,后面以此类推//如果数组中有n个数据,那总共执行n-1轮代码就可以//创建一个数组int[] arr = {1,4,5,2,3,9,5,6};int[] resultArr = bubbleSort(arr);for (int i = 0; i < resultArr.length; i++) {System.out.println(resultArr[i]);}}private static 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 temp = arr[j];arr[j] = arr[j + 1];arr[j + 1] = temp;}}}return arr;}
}
2.选择排序:
特点:
        从0索引开始,拿着每一个索引上的元素跟后面的元素依次比较小的放前面,大的放后面(从小到大情况),以此类推第一轮循环结束后,最小的数据已经确定第二轮循环从1索引开始,以此类推
代码:
public class SelectionSort {public static void main(String[] args) {//从0索引开始,拿着每一个索引上的元素跟后面的元素依次比较//小的放前面,大的放后面(从小到大情况),以此类推//第一轮循环结束后,最小的数据已经确定//第二轮循环从1索引开始,以此类推//创建数组int[] arr = {4,3,9,5,6,8,2,1};int[] resultArr = bubbleSort(arr);for (int i = 0; i < resultArr.length; i++) {System.out.println(resultArr[i]);}}public static int[] bubbleSort(int[] arr) {//外循环:表示几轮for (int i = 0; i < arr.length - 1; i++) {//内循环:i后面的所有数据与i进行比较for (int j = i + 1; j < arr.length; j++) {if(arr[i] > arr[j]) {int temp = arr[i];arr[i] = arr[j];arr[j] = temp;}}}return arr;}
}
3.插入排序:
特点:
        将0索引的元素到N索引的元素看做是有序的,把N+1索引的元素到最后一个元素当成是无序的。遍历无序的数据,将遍历到的元素插入有序序列中适当的位置,如遇到相同数据,插在后面。
代码:
public class InsertionSort {public static void main(String[] args) {//将0索引的元素到N索引的元素看做是有序的,把N+1索引的元素到最后一个元素当成是无序的。//遍历无序的数据,将遍历到的元素插入有序序列中适当的位置,如遇到相同数据,插在后面。//创建数组int[] arr = {1,6,5,3,9,7,16,1,22,3};int[] resultArr = insertionSort(arr);for (int i = 0; i < resultArr.length; i++) {System.out.println(resultArr[i]);}}public static int[] insertionSort(int[] arr) {//判断有序元素个数int index = 0;for (int i = 1; i < arr.length; i++) {if(arr[index] < arr[index + 1]) {index++;} else {break;}}//index为最后一个有序元素的索引//有序元素后面的每个元素要插入有序元素中   插入后有序元素加1   索引也++//我的其他思路   复杂了。。/*for (; index < arr.length - 1; index++) {int i = index + 1;for(int j = index; j >= 0; j--) {if(arr[i] >= arr[j]) {break;} else {//有序元素后面的无序元素只要比前面的小就交换位置int temp = arr[i];arr[i] = arr[j];arr[j] = temp;i--;continue;}}}*///从有序数组后的第一个元素到最后一个元素for (int i = index + 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--;}}return arr;}
}
4.快速排序

        这里展示快速排序之前要先学会递归思想,我先来放两个递归思想的小练习

递归练习一 题目及代码:
public class RecursionAlgorithmTest1 {public static void main(String[] args) {//核心:找出口 找规律//方法中再次调用方法时,参数应更接近出口//求1~100所有整数的和int sum = getSum(100);System.out.println(sum);}//1~100所有整数的和 = 100 + 1~99的和//1~99的和 = 99 + 1~98的和//…………public static int getSum(int num) {//出口if(num == 1) {return 1;}return num + getSum(num - 1);}
}
递归练习二 题目及代码:
public class RecursionAlgorithmTest2 {public static void main(String[] args) {//需求:用递归求5的阶乘,并把结果在控制台输出int factorail = getFactorail(5);System.out.println(factorail);}//5的阶乘 = 5 * 4的阶乘//4的阶乘 = 4 * 3的阶乘//…………public static int getFactorail(int num) {//出口if(num == 1) {return 1;}return num * getFactorail(num - 1);}
}

        接下来开始讲解快速排序:

过程:
//将排序范围中的第一个数字作为基准数,在定义两个变量start,end
//start从前往后找比基准数大的,end从后往前找比基准数小的。
/*找到之后交换start和end指向的元素,并循环这一过程,直到start和end处于同一个位置,
该位置是基准数在数组中应存入的位置,再让基准数归位*/
//归为后的效果:基准数左边的都比基准数小,右边的都比基准数大
代码演示:
public class QuickSort {public static void main(String[] args) {//创建数组int[] arr = {6,2,3,1,7,5,8};int start = 0;int end = arr.length - 1;quickSort(arr, start, end);for (int i = 0; i < arr.length; i++) {System.out.println(arr[i]);}}private static void quickSort(int[] arr, int i, int j) {//出口if(i >= j) {return;}int start = i;int end = j;//基准数int baseNumber = arr[i];while(start != end) {//end从右往左开始找比基准数小的数while(true) {if(end <= start || arr[end] < baseNumber) {break;}end--;}//start从左往右开始找比基准数大的数while(true) {if(end <= start || arr[start] > baseNumber) {break;}start++;}//交换位置int temp = arr[end];arr[end] = arr[start];arr[start] = temp;}//将基准数与当前start和end索引所在位置交换int temp = arr[i];arr[i] = arr[start];arr[start] = temp;//基准数左边继续重复刚才所做的事quickSort(arr, i, start - 1);//基准数右边继续重复刚才所做的事quickSort(arr, start + 1, j);}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/804241.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

SpringMVC:搭建第一个web项目并配置视图解析器

&#x1f449;需求&#xff1a;用spring mvc框架搭建web项目&#xff0c;通过配置视图解析器达到jsp页面不得直接访问&#xff0c;实现基本的输出“hello world”功能。&#x1f469;‍&#x1f4bb;&#x1f469;‍&#x1f4bb;&#x1f469;‍&#x1f4bb; 1 创建web项目 1…

如何解决Python包管理问题:ERROR: Could not find a version that satisfies the requirement

如何解决Python包管理问题&#xff1a;“ERROR: Could not find a version that satisfies the requirement” 文章目录 如何解决Python包管理问题&#xff1a;“ERROR: Could not find a version that satisfies the requirement”错误描述问题分析解决方案检查包名确保网络连…

【JVM】面试题汇总

JVM1. 什么是JVM&#xff1f;2. 了解过字节码文件的组成吗&#xff1f;3. 什么是运行时数据区4. 哪些区域会出现内存溢出5. JVM在JDK6-8之间在内存区域上有什么不同 6. 类的生命周期 7. 什么是类加载器&#xff1f;类加载器有哪几种 8. 什么是双亲委派机制&#xff1f;有什么好…

“国字号”荣誉、全国试点,侨乡群众身边的“放心”公证处

日前&#xff0c;我市五邑公证处获评“全国公共法律服务工作先进集体”称号。 走进公证处&#xff0c;首先映入眼帘的是一间宽敞明亮的大厅&#xff0c;办证点内还设置多个独立办证室&#xff0c;工作人员热情地为前来办理业务的市民提供专业、人性化的公证服务。江门市五邑公证…

Windows上面搭建Flutter Android运行环境

Flutter Android环境搭建 电脑上面安装配置JDK电脑上下载安装Android Studio电脑上面下载配置Flutter Sdk &#xff08;避坑点一&#xff09;下载SDK配置对应的环境变量 到path 电脑上配置Flutter国内镜像运行 flutter doctor命令检测环境是否配置成功创建运行Flutter项目&…

ARM单片机的GPIO口在控制不同LED、按键时的设置

个人备忘&#xff0c;不喜勿喷。 GPIO口在驱动共阴极、共阳极LED灯时需要不同的初始化设置 对于这一类的led灯&#xff1a; 最好选择推挽、上拉、高速输出&#xff0c;同时IO口初始化时需要拉高。 上面这种需要下拉输入&#xff1b; 上图这种需要上拉输入&#xff0c;这样才…

vue点击上传图片并实现图片预览功能,并实现多张图片放到一个数组中进行后端请求(使用原生input)

一、将 File 对象转成 BASE64 字符串 &#xff08;FileReader&#xff09; <template><div><!-- 用来显示封面的图片 --><!-- <img src"/assets/images/cover.jpg" alt"" class"cover-img" ref"imgRef" />…

html基础(2)(链接、图像、表格、列表、id、块)

1、链接 <a href"https://www.example.com" target"_blank" title"Example Link">Click here</a> 在上示例中&#xff0c;定义了一个链接&#xff0c;在网页中显示为Click here&#xff0c;鼠标悬停指示为Example Link&#xff0c…

Java(多线程)

一、基本概念 进程&#xff1a;一个具有一定独立功能的程序关于某个数据集合的一次运行活动。它是操作系统动态执行的基本单元&#xff0c;在传统的操作系统中&#xff0c;进程既是基本的分配单元&#xff0c;也是基本的执行单元。线程&#xff1a;操作系统中能够进行运算的最…

java Web课程管理系统用eclipse定制开发mysql数据库BS模式java编程jdbc

一、源码特点 JSP 课程管理系统是一套完善的web设计系统&#xff0c;对理解JSP java 编程开发语言有帮助&#xff0c;系统具有完整的源代码和数据库&#xff0c;系统主要采用B/S模式开发。开发环境为TOMCAT7.0,eclipse开发&#xff0c;数据库为Mysql5.0&#xff0c;使用ja…

贪心算法|406.根据身高重建队列

力扣题目链接 class Solution { public:static bool cmp(const vector<int>& a, const vector<int>& b) {if (a[0] b[0]) return a[1] < b[1];return a[0] > b[0];}vector<vector<int>> reconstructQueue(vector<vector<int>…

骑砍2霸主MOD开发(2)-基础开发环境搭建

一.骑砍2霸主程序架构 二.骑砍2霸主C#接口层代码查看 1.C#反编译工具dnspy下载: 2.骑砍2霸主游戏引擎接口查看: 例如IMBAgent interface接口: #调用TaleWorlds.Native.dll中的函数 [EngineMethod("get_movement_flags", false)] uint GetMovementFlags(UIntPtr agen…

Visual Studio Code SSH 连接远程服务器

Visual Studio Code通过 SSH 连接远程服务器并实现免密登录&#xff0c;你可以按照以下步骤进行操作&#xff1a; 1. **安装插件**&#xff1a;首先&#xff0c;在 VS Code 中安装 "Remote - SSH" 插件。打开 VS Code&#xff0c;点击左侧的扩展图标&#xff0c;搜索…

微服务学习3

目录 1.微服务保护 1.1.服务保护方案 1.1.1.请求限流 1.1.2.线程隔离 1.1.3.服务熔断 1.2.Sentinel 1.2.1.微服务整合 1.2.2.请求限流 1.3.线程隔离 1.3.1.OpenFeign整合Sentinel 1.3.2.配置线程隔离 1.4.服务熔断 1.4.1.编写降级逻辑 1.4.2服务熔断 2.分布式事…

mp4转flv怎么转?电脑怎么把视频转成flv?

MP4&#xff08;MPEG-4 Part 14&#xff09;是一种多媒体容器格式&#xff0c;广泛用于包含视频、音频、字幕等多种数据流。MP4因其高度灵活性、压缩效率和兼容性成为视频领域的主流格式&#xff0c;支持范围涵盖从在线视频到移动设备的各类应用场景。 FLV文件格式的多个优点 …

scFed:联邦学习用于scRNA-seq分类

scRNA-seq的出现彻底改变了我们对生物组织中细胞异质性和复杂性的理解。然而&#xff0c;大型&#xff0c;稀疏的scRNA-seq数据集的隐私法规对细胞分类提出了挑战。联邦学习提供了一种解决方案&#xff0c;允许高效和私有的数据使用。scFed是一个统一的联邦学习框架&#xff0c…

Spring Validation解决后端表单校验

NotNull&#xff1a;从前台传递过来的参数不能为null,如果为空&#xff0c;会在控制台日志中把message打印出来 Range&#xff1a;范围&#xff0c;最大多少&#xff0c;最小多少 Patten&#xff0c;标注的字段值必须符合定义的正则表达式&#xff08;按照业务规则&#xff0…

Android OOM问题定位、内存优化

一、常用工具&#xff1a; 1、LeakCanary val refWatcher: RefWatcher? TestApp.getRefWatcher(activity) refWatcher?.watch(activity);//检测是否有泄露&#xff0c;即触发GC回收&#xff0c;看activity是否被回收&#xff0c;没有被回收就是泄露了。 二、常见的几种内…

TCP 重传、滑动窗口、流量控制、拥塞控制(计算机网络)

重传机制 TCP 针对数据包丢失的情况&#xff0c;会用重传机制解决。 接下来说说常见的重传机制&#xff1a; 超时重传快速重传SACKD-SACK 超时重传 重传机制的其中一个方式&#xff0c;就是在发送数据时&#xff0c;设定一个定时器&#xff0c;当超过指定的时间后&#xff0c…

实验2 路由器基本配置

实验2 路由器基本配置 一、 原理描述二、 实验目的三、 实验内容四、 实验步骤1.建立实验拓扑2.基础配置3.配置路由器接口IP地址4.查看路由器配置信息5.连通性测试6.使用抓包工具 一、 原理描述 华为设备支持多种配置方式&#xff0c;操作人员要熟悉使用命令行的方式进行设备管…