leetcode33

【题目】

顺序排列的数组,每个点值不同。以某个点进行旋转(其实就是前后两段交换位置),对旋转后数组搜索有无target,没有-1,有返回位置

(变式81不同点在于会出现重复数字)

There is an integer array nums sorted in ascending order (with distinct values).

Prior to being passed to your function, nums is rotated at an unknown pivot index k (0 <= k < nums.length) such that the resulting array is [nums[k], nums[k+1], ..., nums[n-1], nums[0], nums[1], ..., nums[k-1]] (0-indexed). For example, [0,1,2,4,5,6,7] might be rotated at pivot index 3 and become [4,5,6,7,0,1,2].

Given the array nums after the rotation and an integer target, return the index of target if it is in nums, or -1 if it is not in nums.

You must write an algorithm with O(log n) runtime complexity.

 

Example 1:

Input: nums = [4,5,6,7,0,1,2], target = 0
Output: 4

Example 2:

Input: nums = [4,5,6,7,0,1,2], target = 3
Output: -1

Example 3:

Input: nums = [1], target = 0
Output: -1

 

【思路】

找到旋转点P,顺序排列,那第一个后项比前项小的就是旋转点

将其分为[0,P)和[P,nums.length)两段分别做二分查找

最后输出两段中返回值大的(-1/任意位置)

100%

 

【代码】

 

class Solution {
   public int search(int[] nums, int target) {
        int p=0;
        for(int i=1;i<nums.length;i++){
            if(nums[i]<nums[i-1])
                p=i;
        }

        return Math.max(bs(nums,target,0,p),bs(nums,target,p,nums.length));
    }
    
    public int bs(int[] nums,int target,int left,int right){
        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;
        }
        return -1;
    }
}

 

 leetcode81

【题目】

和31题不同的是,会出现重复数字

There is an integer array nums sorted in non-decreasing order (not necessarily with distinct values).

Before being passed to your function, nums is rotated at an unknown pivot index k (0 <= k < nums.length) such that the resulting array is [nums[k], nums[k+1], ..., nums[n-1], nums[0], nums[1], ..., nums[k-1]] (0-indexed). For example, [0,1,2,4,4,4,5,6,6,7] might be rotated at pivot index 5 and become [4,5,6,6,7,0,1,2,4,4].

Given the array nums after the rotation and an integer target, return true if target is in nums, or false if it is not in nums.

You must decrease the overall operation steps as much as possible.

 

Example 1:

Input: nums = [2,5,6,0,0,1,2], target = 0
Output: true

Example 2:

Input: nums = [2,5,6,0,0,1,2], target = 3
Output: false

 【测试】

易错的testcase

[2,2,2,3,2,2,2] 3

[1,2,1] 2

【思路】

一样的思路,注意边界就行

还有可以优化的地方 

【代码】

 

class Solution {
    public boolean search(int[] nums, int target) {
        int point=0;
        for(int i=1;i<nums.length;i++){
            if(nums[i]<nums[i-1])
                point=i;
        }
        return (bs(nums,0,point,target))||bs(nums,point,nums.length,target);
    }

    public boolean bs(int[] nums,int left,int right,int target){
        while(left<right){
            int mid=left+(right-left)/2;
            if(nums[mid]==target)
                return true;
            else if(nums[mid]>target)
                right=mid;
            else if(nums[mid]<target)
                left=mid+1;
        }
        return false;
    }
}

 

 posted on 2021-08-19 09:05  alau  阅读(27)  评论(0编辑  收藏  举报