ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

二分查找

2022-05-12 18:01:09  阅读:148  来源: 互联网

标签:二分 right target nums int middle 查找 left


二分查找使用时的前提条件:

  1. 查找的内容在逻辑上是有序的。

  2. 查找的数量只能是一个。

二分法的思想:

  1. 选择数组中间的数字与目标值进行比较。

  2. 如果相等,返回答案。

  3. 如果不相等

    • 中间的数字大于目标值,则中间数字向右的所有数字都大于目标值,右边的数字全部排除

    • 中间的数字小于目标值,则中间数字向左的所有数字都小于目标值,左边的数字全部排除

抛去一个错误观念:

当数组长度是偶数时,怎么取最中间的数。千万不要纠结这个问题,这并不影响我们寻找目标数。

记住判断的核心思想:

  • 只要取的数字大于目标数字,就排除右边

  • 只要取得数字小于目标数字,就排除左边

所以数组长度是偶数时,并不一定要取最中间的数,这并不影响怎么排除的问题,无非就是多排除一个数字或者少排除一个数字。

真正影响结果的时,取的哪个中间数字要不要加入下一次判断的查找中,即边界值问题。

边界值问题:

  1. 左闭右闭区间

  2. 左闭右开区间

判断过程中,最重要的两个点:

  1. while循环中 left 与 right 的关系,到底是 left <= right 还是 left < right

  2. 迭代过程中 middle 和 right 的关系,到底是 right = middle - 1 还是 right = middle

左闭右闭区间的情况: 

public static void main(String[] args) {
        int[] nums = new int[]{-1, 0, 3, 9, 11, 13, 22, 27, 33, 57, 66, 77};
​
        //nums是数组,size是数组的大小,target是需要查找的值
        int search = new BinarySearch1().search(nums, nums.length, 33);
        System.out.println(search);
    }
​
    int search(int nums[], int size, int target)
    {
        int left = 0;
        int right = size - 1;   // 定义了target在左闭右闭的区间内,[left, right]
        while (left <= right) { //当left == right时,区间[left, right]仍然有效
            int middle = left + ((right - left) / 2);//等同于 (left + right) / 2,防止溢出
            if (nums[middle] > target) {
                right = middle - 1; //target在左区间,所以[left, middle - 1]
            } else if (nums[middle] < target) {
                left = middle + 1;  //target在右区间,所以[middle + 1, right]
            } else {
                return middle;  //既不在左边,也不在右边,那就是找到答案了
            }
        }
        //没有找到目标值
        return -1;
    }

左闭右开区间的情况:

public static void main(String[] args) {
        int[] nums = new int[]{-1, 0, 3, 9, 11, 13, 22, 27, 33, 57, 66, 77};
​
        //nums是数组,size是数组的大小,target是需要查找的值
        int i = new BinarySearch1().search1(nums, nums.length, 27);
        System.out.println(i);
    }
​
    int search1(int nums[], int size, int target)
    {
        int left = 0;
        int right = size; //定义target在左闭右开的区间里,即[left, right)
        while (left < right) {  //因为left = right的时候,在[left, right)区间上无意义
            int middle = left + ((right - left) / 2);
            if (nums[middle] > target) {
                right = middle; //target 在左区间,在[left, middle)中
            } else if (nums[middle] < target) {
                left = middle + 1;
            } else {
                return middle;
            }
        }
        // 没找到就返回-1
        return -1;
    }

 

 

标签:二分,right,target,nums,int,middle,查找,left
来源: https://www.cnblogs.com/l12138h/p/16263541.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有