Leecode#35刷题之搜索插入位置

题目

给定一个排序数组和一个目标值,在数组中找到目标值,并返回其索引。如果目标值不存在于数组中,返回它将会被按顺序插入的位置。

请必须使用时间复杂度为 O(log n) 的算法。

示例 1:

复制代码
输入: nums = [1,3,5,6], target = 5
输出: 2

示例 2:

复制代码
输入: nums = [1,3,5,6], target = 2
输出: 1

示例 3:

复制代码
输入: nums = [1,3,5,6], target = 7
输出: 4

提示:

  • 1 <= nums.length <= 104
  • -104 <= nums[i] <= 104
  • nums无重复元素升序排列数组
  • -104 <= target <= 104

Java代码

java 复制代码
class Solution {
    public int searchInsert(int[] nums, int target) {
        int left = 0, right = nums.length - 1;

        while (left <= right) {
            int mid = left + (right - left) / 2;

            if (nums[mid] == target) {
                return mid;
            } else if (nums[mid] < target) {
                left = mid + 1;
            } else {
                right = mid - 1;
            }
        }

        return left;
    }
}

核心思路: 标准二分查找。找到了就返回下标,没找到循环结束时 left 就是该插入的位置。


逐行说明:

java 复制代码
int left = 0, right = nums.length - 1;

标准二分框架,left 从 0 开始,right 从末尾开始。

java 复制代码
while (left <= right) {

int mid = left + (right - left) / 2;

left + (right - left) / 2 等价于 (left + right) / 2,但避免整数溢出。

java 复制代码
if (nums[mid] == target) {

return mid; // 找到了,返回下标

} else if (nums[mid] < target) {

left = mid + 1; // 太小,往右找

} else {

right = mid - 1; // 太大,往左找

}

标准二分查找逻辑。

java 复制代码
return left;

关键 :没找到时,循环结束 left > rightleft 就是 target 应该插入的位置。


为什么没找到时 left 就是插入位置?

nums = [1,3,5,6], target = 2 为例:

轮次 left right mid numsmid 操作
1 0 3 1 3 3>2, right=0
2 0 0 0 1 1<2, left=1
退出 1 0 left > right
复制代码
nums: [1, 3, 5, 6]
           ↑
        left=1 (插入位置)

2 应该插在 1 和 3 之间,下标 1 ✓

循环结束时 left 停在第一个大于 target 的位置,正好就是插入位置。


三个示例演示:

target 过程 结果
5 mid=1→3<5, mid=2→5==5 返回 2 ✓
2 mid=1→3>2, mid=0→1<2, left=1 返回 1 ✓
7 mid=1→3<7, mid=2→5<7, mid=3→6<7, left=4 返回 4 ✓

时间复杂度 O(log n),空间复杂度 O(1)。

python代码

python 复制代码
class Solution(object):
    def searchInsert(self, nums, target):
        left, right = 0, len(nums) - 1

        while left <= right:
            mid = left + (right - left) // 2

            if nums[mid] == target:
                return mid
            elif nums[mid] < target:
                left = mid + 1
            else:
                right = mid - 1

        return left
相关推荐
一条泥憨鱼1 小时前
苍穹外卖【day10| 来电提醒和客户催单】
java·后端·websocket·苍穹外卖
SunnyDays10111 小时前
Java 设置 Excel 数据验证:整数、日期、文本长度、下拉列表和时间
java·excel·数据验证·下拉列表
QQ14220784491 小时前
IIS + wfastcgi 部署 Flask 应用实战:从连续 500 到稳定 200 的完整踩坑实录
python
编程_大白1 小时前
@SpringBootTest
java
WiKiLeaks_successor1 小时前
Scipy库里的众数函数不严谨,我把它重构了。
python·scipy
傻啦嘿哟1 小时前
房产数据对比爬虫:同时爬取链家+贝壳+安居客,做房价横向对比
python
我不会起名字3221 小时前
万字总结Golang入门项目
数据结构·经验分享·算法·golang·项目实战·复盘
刘天远1 小时前
Agent最小权限实现:策略表、临时令牌与撤权回归
java·jvm·人工智能·sqlite
6Hzlia1 小时前
【Classic 150 刷题计划】 LeetCode 14. 最长公共前缀 | C++ 纵向扫描法与防越界细节
c++·算法·leetcode