栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

搜索算法--Search Algorithm

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

搜索算法--Search Algorithm

    在java中,我们常用的查找有四种:   

                  1) 顺序(线性)查找  

                  2) 二分查找/折半查找  

                  3) 插值查找  

                  4) 斐波那契查找

一、线性查找

        在数组中进行查找,找到返回下标,找不到返回-1

   //线性查找
    public static int seq(int[] array, int data) {
        for (int i = 0; i < array.length; i++) {
            if (array[i] == data) {
                return i;
            }
        }
        return -1;
    }

 


二、二分查找【查找的数据必须是一个有序的数组】

        不断的将一个数组进行折半处理,判断中间值是否是要查找的数据。如果中间值比查找的值大,就往中间值的左边进行查找,如果中间值比查找的值小,就往中间值的右边进行查找

 代码实现:

    
    public static int binarySearch(int[] array, int start, int end, int findVal) {
        if (start > end) {
            //递归结束条件
            return -1;
        }
        int mid = (start + end) / 2;
        int midVal = array[mid];
        if (findVal > midVal) {
            //右边递归
           return binarySearch(array, mid + 1, end, findVal);
        } else if (findVal < midVal) {
            //左边递归查找
            return  binarySearch(array, start, mid - 1, findVal);
        }
        return mid;
    }

当查找的值数组中有多个时,代码该怎么写:        

        思路:

                当找到相等的值时不要返回,继续向左递归如果还有相等的值就加到一个集合中

,继续向右递归如果有相等的值加到一个集合中,,最终返回一个集合

代码实现:

  
    public static ArrayList binarySearch(int[] array, int start, int end, int findVal) {
        if (start > end) {
            //结束条件
            throw new RuntimeException("没有找到");
        }
        int mid = (start + end) / 2;
        int midVal = array[mid];
        if (findVal > midVal) {
            //右边递归
            return binarySearch(array, mid + 1, end, findVal);
        } else if (findVal < midVal) {
            //左边递归查找
            return binarySearch(array, start, mid - 1, findVal);
        } else {
            //保存结果
            ArrayList list = new ArrayList<>();
            //向左进行查找
            int temp = mid - 1;
            while (true) {
                //因为数组定是有序的,所以相等的值也是连续的
                if (temp < 0 || array[temp] != findVal) {
                    break;
                }
                list.add(temp);
                temp--;
            }
            //增加mid
            list.add(mid);
            //向右查找
            temp = mid + 1;
            while (true) {
                if (temp > end || array[temp] != findVal) {
                    break;
                }
                list.add(temp);
                temp++;
            }

            return list;
        }
    }

 三、插值查找

1、插值查找算法类似于二分查找,不同的是插值查找每次从自适应mid处开始查找。插值查找也需要一个有序的数组

2、将折半查找中的求mid 索引的公式 , low 表示左边索引left, high表示右边索引right. key 就是前面我们讲的  findVal, int mid = low + (high - low) * (key - arr[low]) / (arr[high] - arr[low])  ;

3、对应前面的代码公式: int mid = left + (right – left) * (findVal – arr[left]) / (arr[right] – arr[left])

4、通过上面的公式,mid直接定位到查找元素的位置上,只需要查找一次

  
    public static int inertValSearch(int[] array ,int left ,int right ,int findVal){
        System.out.println("查找次数"); //1次
        //获取mid
        //!!!!!!直接定位到要超找元素的下标
        int mid =  left + (right - left) * (findVal - array[left]) / (array[right] - array[left]);
        //获取中间值
        int midVal = array[mid] ;

        //放置越界
        //当查找的比第一个数小,比最后一个大时,停止查询
        if(left>right || findVal < array[0] || findVal > array[array.length-1]){
            return -1;
        }

        if (findVal > midVal){
            //如果查找的值比中间值大,则右递归
            return inertValSearch(array,mid+1,right,findVal) ;
        }else if (findVal < midVal){
            //查找的值比中间值小,左递归
            return inertValSearch(array,left,mid,findVal);
        }else {
            return mid ;
        }
    }

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/678225.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号