本文最后更新于:2 天前
应用场景 寻找一个数、寻找左侧边界、寻找右侧边界。这三种场景使用统一的框架,while 条件统一用 <=,边界更新统一用 mid ± 1(mid=left + (right - left) / 2,等价于(left + right) / 2,防止整形溢出,便于记忆。
框架模板 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 int binary_search (int [] nums, int target) { int left = 0 , right = nums.length - 1 ; while (left <= right) { int mid = left + (right - left) / 2 ; if (nums[mid] < target) { left = mid + 1 ; } else if (nums[mid] > target) { right = mid - 1 ; } else if (nums[mid] == target) { return mid; } } return -1 ; }int left_bound (int [] nums, int target) { int left = 0 , right = nums.length - 1 ; while (left <= right) { int mid = left + (right - left) / 2 ; if (nums[mid] < target) { left = mid + 1 ; } else if (nums[mid] > target) { right = mid - 1 ; } else if (nums[mid] == target) { right = mid - 1 ; } } if (left < 0 || left >= nums.length) { return -1 ; } return nums[left] == target ? left : -1 ; }int right_bound (int [] nums, int target) { int left = 0 , right = nums.length - 1 ; while (left <= right) { int mid = left + (right - left) / 2 ; if (nums[mid] < target) { left = mid + 1 ; } else if (nums[mid] > target) { right = mid - 1 ; } else if (nums[mid] == target) { left = mid + 1 ; } } if (right < 0 || right >= nums.length) { return -1 ; } return nums[right] == target ? right : -1 ; }
具体问题模板 题目解读 :1、确定 x, f(x), target 分别是什么,并写出函数 f 的代码 。2、找到 x 的取值范围作为二分搜索的搜索区间,初始化 left 和 right 变量 。3、根据题目的要求,确定应该使用搜索左侧还是搜索右侧的二分搜索算法,写出解法代码 。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 int f (int x) { }int solution (int [] nums, int target) { if (nums.length == 0 ) return -1 ; int left = ...; int right = ... + 1 ; while (left < right) { int mid = left + (right - left) / 2 ; if (f(mid) == target) { } else if (f(mid) < target) { } else if (f(mid) > target) { } } return left; }
算法步骤 1、确定 x(求解目标), f(x)(target随x的单调关系), target(满足的阈值) 分别是什么,并写出函数 f 的代码 。2、找到 x 的取值范围作为二分搜索的搜索区间,初始化 left 和 right 变量 。3、根据题目的要求,确定应该使用搜索左侧还是搜索右侧的二分搜索算法,写出解法代码 。