折半查找(二分查找)的实现(Java)与讲解-常见数据结构

折半查找的实现(Java)与讲解-常见数据结构

1、讲解

也称二分搜索,对数搜索,是用来在一个有序数组中查找某一元素的算法。

例子:在一个升序数组中查找一个数。每次考察数组当前部分的中间元素(middle),如果中间元素刚好是目标元素(target),就结束搜索。如果中间元素小于所查找的值,就在数组左半部分[left,middle]查找;如果中间元素大于所查找的值,就在数组右半部分[middle,right]查找。

二分搜索法可以用来查找满足某一条件的最大(最小)值。

要求满足某种条件的最大值最小可能情况(最大值最小化),首先的想法是从小到大枚举这个作为答案的[最大值],然后去判断是否合法。若答案单调,就可以使用二分搜索法来更快的找到答案

使用二分搜索法解决[最大值最小化]条件:

  1. 答案在一个固定区间内
  2. 比较容易判断某个值是否符合条件
  3. 可行解对于区间满足一定的单调性(x符合条件,那么x-1或x+1也符合条件)
  • 时间复杂度:最优情况O(1),平均/最坏时间复杂度O(log n)

2、实现

算法思路

假设目标值在闭区间[l,r]中,每次将区间长度缩小一半,当l=mid时,找到目标值

区间[l,r]划分为[l,mid-1][mid+1,r];更新操作为r=mid-1l=mid+1。

package top.alibra.algorithm;

public class Dichotomy {
    
    
    //折半查找(二分法查找):前提数组有序
    public static int dichotomySearch(int[] nums, int target) {
    
    
        if(nums == null || nums.length == 0){
    
     //判断数组为空
            return -1;
        }
        int l = 0, r = nums.length - 1; //设置左右边界
        while(l <= r){
    
    
            int mid = l + (r-l) / 2; // 等同于mid=(l+r)/2,这种写法是为了防止数组越界,也可以写为(l+r) >>> 1
            if(nums[mid] == target){
    
     //最终target=mid,返回mid
                return mid;
            }else if(nums[mid] < target) {
    
     //目标值在(mid,r]之间
                l = mid + 1;
            }else {
    
      //目标值在[l,mid)之间
                r = mid - 1;
            }
        }
        // 最后判断: l>r 即数组不存在
        return -1;
    }

    //测试
    public static void main(String[] args) {
    
    
        //定义一个属数组
        int[] arr={
    
    1,3,9,11,12,13,17,24,51,86,87,92,99};
        int num = dichotomySearch(arr,17);
        System.out.println(num);
    }


}

猜你喜欢

转载自blog.csdn.net/qq_46138492/article/details/129265046