8. <tag-数组和二分查找_1>-lt.704-二分查找 + lt.33-搜索旋转排序数组 +lt.34-在排序数组中查找元素的第一个和最后一个位置 + lt.35-搜索插入位置 (待完善)

lt.704 二分查找

[案例需求]
在这里插入图片描述

[思路分析]

  1. 二分法典型例题, 有什么好说的, 我秒了(误)
  2. 口误啊口误, 可不敢说秒二分. 本题是二分法的标准入门题, 本意还是通过二分查找值, 是前面讲过的二分查找的第一个模板, 在这里就不讲太多了, 好好看下前面文章哈.

[代码实现]

	class Solution {
    
    
    public int search(int[] nums, int target) {
    
    
        // // 左开右闭

        // int left = 0;
        // int right = nums.length;

        // while(left < right){
    
    

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

        //二分查找, 左闭右闭
        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 -1;
    }
}

lt.33-搜索旋转排序数组

[案例需求]
在这里插入图片描述

[思路分析]

[代码实现]

class Solution {
    
    
    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;


            //遍历部分有序的序列, 对这部分有序的序列进行二分查找

            //在有序的左半段(nums[left] < nums[mid])
            if(nums[left] <= nums[mid]){
    
    
                
                //缩小左半段的边界(左半段的左边界), 去除组织这个序列单调的数
                if(nums[left] <= target && nums[mid] > target){
    
    
                    right = mid - 1; //左半段的单调序列
                }else{
    
    
                    left = mid + 1; //右半段的单调序列
                }
                
            }else{
    
     //右半段有序的序列

                //缩小右边届的左半段
                if(nums[mid] < target && nums[right]  >= target){
    
    
                    left = mid + 1;	//右半段的单调序列
                }else{
    
    
                    right = mid - 1;//左半段的单调序列
                }
            }
        }
        return -1;
    }
}

lt.34-在排序数组中查找元素的第一个和最后一个位置

[案例需求]

[思路分析]

[代码实现]

class Solution {
    
    
    public int[] searchRange(int[] nums, int target) {
    
    
        // 要求 o(logn), 并且是有序序列, 二分法走起
        
        //特例
        if(nums.length == 0) return new int[]{
    
    -1,-1};        
        //左边界和右边界, 
        return new int[]{
    
    bsfirst(nums, target), bslast(nums, target)};
    }

    public int bsfirst(int[] nums, int target){
    
    
        int left = 0;
        int right = nums.length - 1;

        while(left <= right){
    
    
            int mid = left + ((right - left) >> 1);

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

        return -1;
    }

    public int bslast(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){
    
    
                left = mid + 1;
            }else if(nums[mid] == target){
    
    
                if(mid == nums.length - 1 || nums[mid + 1] != target){
    
    
                    return mid;
                }else{
    
    
                    left = mid + 1;
                }
            }
        }
           return -1;
    }
 
}

lt.35-搜索插入位置

[案例需求]
在这里插入图片描述

[思路分析]

[代码实现]

class Solution {
    
    
    public int searchInsert(int[] nums, int target) {
    
    
    //     //logn 二分
    //     int left = 0;
    //     int right = nums.length - 1;
    //     int mid = 0;

    //     while(left <= right){
    
    
    //         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 left;
    // }
        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 left;
    }
}

おすすめ

転載: blog.csdn.net/nmsLLCSDN/article/details/121353143