33.搜索旋转排序数组(Search in Rotated Sorted Array)

mac2026-08-04  1

33.搜索旋转排序数组 Search in Rotated Sorted Array

题解二分法算法流程:复杂度分析PythonJava(待完成)

题解

本题看到时间复杂度需要在 O ( log ⁡ n ) O(\log n) O(logn)级别,所以想到二分查找 本题两个特殊之处

有序,可使用二分查找旋转数组,需要找到旋转点,才能进行二分查找

二分法

算法流程:

特判:数组长度为0,返回-1. 数组长度为1,若 n u m s [ 0 ] = = t a r g e t nums[0]==target nums[0]==target,返回0,否则返回-1。(这个特例无法按照算法流程计算,所以需要单独判断)二分法寻找旋转点: 如果首元素小于尾元素,说明未旋转,返回0定义左指针 l l l和右指针 r r r,当 l < = r l<=r l<=r时,进入循环,接下来有两种写法,但是始终返回旋转点为最小值的索引: r o t a t e = ( l + r ) / / 2 rotate=(l+r)//2 rotate=(l+r)//2,如果 n u m s [ r o t a t e ] < n u m s [ r o t a t e − 1 ] nums[rotate]<nums[rotate-1] nums[rotate]<nums[rotate1],此时返回 r o t a t e rotate rotate,判断是否满足 n u m s [ r o t a t e ] > n u m s [ r ] nums[rotate]>nums[r] nums[rotate]>nums[r],若满足说明旋转点在右端,令 l = r o t a t e + 1 l=rotate+1 l=rotate+1,否则在左端,令 r = r o t a t e − 1 r=rotate-1 r=rotate1 r o t a t e = ( l + r ) / / 2 rotate=(l+r)//2 rotate=(l+r)//2,如果 n u m s [ r o t a t e ] > n u m s [ r o t a t e + 1 ] nums[rotate]>nums[rotate+1] nums[rotate]>nums[rotate+1],此时返回 r o t a t e + 1 rotate+1 rotate+1,判断是否满足 n u m s [ r o t a t e ] < n u m s [ l ] nums[rotate]<nums[l] nums[rotate]<nums[l],若满足说明旋转点在左端,令 r = r o t a t e − 1 r=rotate-1 r=rotate1,否则在右端,令 l = r o t a t e + 1 l=rotate+1 l=rotate+1。 若旋转点索引 r o t a t e i n d e x = 0 rotateindex=0 rotateindex=0,说明未旋转,则直接二分查找 f i n d ( 0 , n − 1 ) find(0,n-1) find(0,n1),返回索引判断 t a r g e t > = n u m s [ 0 ] target>=nums[0] target>=nums[0],如果满足,说明在旋转段的较大段, f i n d ( 0 , r o t a t e i n d e x ) find(0,rotateindex) find(0,rotateindex),否则 f i n d ( r o t a t e i n d e x , n − 1 ) find(rotateindex,n-1) find(rotateindex,n1)

复杂度分析

时间复杂度: O ( log ⁡ n ) O(\log n) O(logn)+ O ( log ⁡ n ) O(\log n) O(logn), O ( log ⁡ n ) O(\log n) O(logn)空间复杂度: O ( 1 ) O(1) O(1)

Python

class Solution: def search(self, nums: List[int], target: int) -> int: def find_rotateindex(l,r): if(nums[l]<nums[r]): return 0 while(l<=r): rotate=(l+r)//2 if(nums[rotate]<nums[rotate-1]): return rotate if(nums[rotate]>nums[r]): l=rotate+1 else: r=rotate-1 #print(find_rotateindex(0,len(nums)-1)) def find(l,r): while(l<=r): mid=(l+r)//2 if(nums[mid]==target): return mid if(nums[mid]>target): r=mid-1 else: l=mid+1 return -1 n=len(nums) if(n==0): return -1 if(n==1): return 0 if(nums[0]==target) else -1 rotateindex=find_rotateindex(0,n-1) if(rotateindex==0): return find(0,n-1) if(target>=nums[0]): return find(0,rotateindex) else: return find(rotateindex,n-1)

Java(待完成)

最新回复(0)