1-leetcode35. 搜索插入位置
注意:×
- 看Labuladong的书,知道
while
的判断符号跟left right
的关系
public int searchInsert(int[] nums, int target) {int left = 0;int right = nums.length - 1;while (left <= right) {int mid = left + (right - left) / 2;if (nums[mid] == target) {return mid;} else if (nums[mid] > target) {right = mid - 1;} else if (nums[mid] < target) {left = mid + 1;}}return right+1;}
leetcode74. 搜索二维矩阵
注意:√
- 跟之前一个题目很像,这种矩阵直接从左上角或者右下角进行查找即可
public boolean searchMatrix(int[][] matrix, int target) {int n = 0;int m = matrix[0].length - 1;while (n < matrix.length && m >= 0) {if (matrix[n][m] == target){return true;} else if (matrix[n][m] > target) {m--;} else if (matrix[n][m] < target) {n++;}}return false;}
3-leetcode34. 在排序数组中查找元素的第一个和最后一个位置
注意:×
- 注意找左边界,是right移动–这个其实没问题
- 问题是:你移动的时候不可以
right == mid
,这样会死循环的(其实写的时候就能发现这个问题)所以直接给变化的值,因为后面会判断结果的 - 左边界,最下面的判读是判断左边界
- 右边界,最下面的判断是判断右边界
public int[] searchRange(int[] nums, int target) {if (nums.length == 0) {return new int[]{-1, -1};}int[] arr = new int[2];arr[0] = findLeftBound(nums, target);arr[1] = findRightBound(nums, target);return arr;}private int findRightBound(int[] nums, int target) {int left = 0;int 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) {return -1;}return nums[right] == target ? right : -1;}private int findLeftBound(int[] nums, int target) {int left = 0;int right = nums.length - 1;while (left <= right) {int mid = left + (right - left) / 2;if (nums[mid] == target) {right = mid - 1;} else if (nums[mid] > target) {right = mid - 1;} else if (nums[mid] < target) {left = mid + 1;}}if (left == nums.length){return -1;}return nums[left] == target? left: -1;}
4-leetcode33. 搜索旋转排序数组
注意:×
- 通过最左边的数字跟
nums[mid]
进行对比,可以得到左边是 有序还是右边是有序的 - 然后判断target的落点
- 注意target和nums[left]的值的对比,不要漏掉相等的情况,即:
if (nums[mid] > target || nums[left] **<=** target){
public int search(int[] nums, int target) {int left = 0;int right = nums.length - 1;while (left <= right) {int mid = left + (right - left) / 2;if (nums[mid] == target){return mid;} else if (nums[left] <= nums[mid]) {// 左边是有序的if (nums[mid] < target || nums[left] > target){left = mid + 1;}else {right = mid - 1;}} else if (nums[left] > nums[mid]) {// 右边虽然反转了,但是右边是有序的if (nums[mid] > target || nums[left] <= target){right = mid - 1;}else {left = mid + 1;}}}return -1;}
5-leetcode153. 寻找旋转排序数组中的最小值
注意:×
- 这个题不能跟上面那个题一样比较左边的值,会出错,因为上面那个只要找到哪边有序就行,但是在这题里面,有序不代表最小,
nums[mid] < nums[left]
无法得到最小值的位置,可能在左边也可能在右边 - 因为要找最小的那个的值,没有
target'
所以调整了right
的修改策略,注意注意!!!!!!!!!! - 第一编写反正是有点怪怪的感觉,不行就记下来吧
public int findMin(int[] nums) {int left = 0;int right = nums.length - 1;while (left < right) {int mid = left + (right - left) / 2;if (nums[right] < nums[mid]) {left = mid + 1;} else {right = mid;}}return nums[left];}