[LeetCode704.二分查找]|刷题打卡

490 阅读3分钟

一、题目描述:

给定一个 n 个元素有序的(升序)整型数组 nums 和一个目标值 target  ,写一个函数搜索 nums 中的 target,如果目标值存在返回下标,否则返回 -1。

难度:简单。

示例1:

输入: nums = [-1,0,3,5,9,12], target = 9
输出: 4
解释: 9 出现在 nums 中并且下标为 4

示例2:

输入: nums = [-1,0,3,5,9,12], target = 2
输出: -1
解释: 2 不存在 nums 中因此返回 -1

提示:

  1. 你可以假设 nums 中的所有元素是不重复的。
  2. n 将在 [1, 10000]之间。
  3. nums 的每个元素都将在 [-9999, 9999]之间。

相关知识:二分查找。

二、思路分析:

考察点与思想

这道题考察的点很简单,是算法里面比较常见的二分查找,也就是考察对二分法的理解。

二分查找一般有以下步骤:

  1. 预处理-如果待求解数组未排序,则需要考虑先进行排序;
  2. 二分查找-使用循环或递归在每次比较后将查找空间划分为两半;
  3. 后处理-继续在剩余空间中确定可行的候选者。

思路和问题

做题时,思路并不难理解,基于二分法。

  1. 每次取数组中间值 mid 与目标值 target 进行比较;
  2. 如果 target == mid,则说明找到目标值,直接返回结果;
  3. 如果 target > mid,则说明目标值在右区间,要收缩左边界,则 left = mid + 1;
  4. 反之,说明目标值在左区间,收缩右边界,则 right = mid - 1;
  5. 继续循环 2-4 步,直到 left > right 时结束循环;
  6. 如果搜索区间中存在目标值,则会在循环中返回,如果循环结束还找不到,说明不存在,返回 -1。

其中的关键点是要把握好各个边界点。

  1. 循环结束的点,left 和 right 相等时也是处于求解区间的,所以得继续循环;
  2. 假设目标值处于求解区间,则在结束循环后是已经返回解了;
  3. 如果不存在,需要返回 -1。

三、AC 代码:

int search(int* nums, int numsSize, int target){
    // 查找区间[left,right]
    int l = 0;
    int r = numsSize - 1;
    int mid = 0;
    while(l <= r) {
        mid = l + (r-l)/2;
        if(target == nums[mid]) {return mid;}
        if(target > nums[mid]) {
            l = mid+1;
        }else {
            r = mid-1;
        }
    }
    return -1;
}

四、总结:

这个算法是简单的二分查找,通过寻找目标值得到求解。

但是在实际情况下,可能不总是直接搜索特定值,有可能会以让你寻找最左/右边满足条件的值、寻找最左/右插入位置,或者让你在局部有序的数组中寻找满足条件的值等多种形式出现。

但是万变不离其宗,核心思想都是尽量在每次处理后都将问题的规模缩小到原来的一半,直到得到满足条件的解或者超出边界。

本文正在参与「掘金 2021 春招闯关活动」, 点击查看 活动详情