原题
二分与排序简单2 种解法

#704二分查找

在严格升序数组中查找 target,存在则返回下标,否则返回 -1。

#数组#二分查找

原题

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

你必须编写一个具有 O(log n) 时间复杂度的算法。


示例 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. 闭区间写法始终维护答案若存在则位于 [left, right],循环条件必须是 left <= right。

解法 1:迭代二分

比较中点后排除不可能包含目标的一半闭区间。

  • 时间复杂度: O(log n)

  • 空间复杂度: O(1)

JAVA
final class Solution {
    public int search(int[] nums, int target) {
        int left = 0, right = nums.length - 1;
        // 闭区间不变量:target 若存在,始终位于 [left, right]
        while (left <= right) {
            // 差值写法避免 left + right 发生整数溢出
            int middle = left + (right - left) / 2;
            if (nums[middle] == target) return middle;
            // middle 已比较过,收缩时必须将其排除
            if (nums[middle] < target) left = middle + 1;
            else right = middle - 1;
        }
        return -1;
    }
}

解法 2:递归二分

递归传递仍可能包含目标的闭区间,区间为空时失败。

  • 时间复杂度: O(log n)

  • 空间复杂度: O(log n),递归栈

JAVA
final class Solution {
    public int search(int[] nums, int target) {
        return search(nums, target, 0, nums.length - 1);
    }

    private int search(int[] nums, int target, int left, int right) {
        // 闭区间为空时说明所有候选位置均已排除
        if (left > right) return -1;
        int middle = left + (right - left) / 2;
        if (nums[middle] == target) return middle;
        // 递归只传递仍可能包含 target 的半侧,并排除已比较的 middle
        if (nums[middle] < target) return search(nums, target, middle + 1, right);
        return search(nums, target, left, middle - 1);
    }
}

边界与易错点

  • 中点使用 left + (right - left) / 2 避免加法溢出。
  • Q074_binarySearch 的题意实际是 LeetCode 704,不是 74,已与 Q704 合并。

整理来源

由旧仓库源码复核、去重并整理;展示代码已按 Java 21 语义修正明显问题。

  • easy/Q074_binarySearch.java
  • easy/Q704_binarysearch.java