【剑指offer】NC105 二分查找-II [Go语言]

191 阅读2分钟

Offer 驾到,掘友接招!我正在参与2022春招系列活动-刷题打卡任务,点击查看活动详情

题目

描述

请实现有重复数字的升序数组的二分查找

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

数据范围:0≤n≤100000 

进阶:时间复杂度O(logn),空间复杂度O(n)

示例1

输入:

[1,2,4,4,5],4

返回值:

2

说明:

从左到右,查找到第1个为4的,下标为2,返回2    

示例2

输入:

[1,2,4,4,5],3

返回值:

-1

示例3

输入:

[1,1,1,1,1],1

返回值:

0

题解

这个其实是很基本的二分查找,二分一般都是用在有序的数组上,就是将每一次的数组都定一个 l 为左值,定一个 r 为右值。

然后mid就是l和r的中间值。但是注意一点求中点的话,是左边加上右边减去左边的一半的值。 另外还有一点,这里要的是找到target的第一个值,所以还要进行一次向前递进的操作。

AC Code

func search( nums []int ,  target int ) int {
(1)    l,r := 0,len(nums)-1
(2)    index := -1
(3)    for l <= r {
(4)        mid :=l + (r-l) / 2
        if nums[mid] > target {
(5)            r = mid-1
        } else if nums[mid] < target {
(6)            l = mid+1
        } else if nums[mid] == target {
(7)            for mid > 0 && nums[mid-1] == nums[mid] {
(8)                mid--
            }
            return mid
        }
    }
    return index
}
  • (1) 左边界和右边界
  • (2) index,如果没有就返回-1
  • (3) 当左边大于右边的话,就退出了,就没找到
  • (4) 中间值等于左边加上右边减去左边的一般
  • (5) 如果这个中间值比我们的目标值大就说明,目标值在左边,让右边等于中间下标-1
  • (6) 如果这个中间值比我们的目标值小就说明,目标值在右边,让左边等于中间下标+1
  • (7) 这里的操作主要是对找到第一个值
  • (8) 如果是重复的话就进行mid--,直到已经不是重复的了