LeetCode T1095.Find in Mountain Array/山脉数组中查找目标值
由题意可得这是一个山峰形数组的查找类问题,对于山峰形数组,我们可以将其看作是递增和递减的两个有序数组的合并,而对于单一的有序数组,可以很容易的使用二分查找。因此,解题思路很清晰,即找出最高峰,以最高峰为界划分成前后两个有序数组,对两个数组分别二分查找,最后返回题目需要的结果。
而在这样的步骤中,求最高峰的下标可以用二分查找,对后续的数组又可以两次二分查找,因此在整个算法过程中共使用了3次二分查找,时间复杂度为O(log(n)),在我自己的代码中,变量的定义为常数个,因此空间复杂度为O(1)。
我的题解代码如下,在leetcode上运行时间4ms,内存占用6MB
int BiSearch_Increase(MountainArray* mountainArr,int first,int end,int target){//从小到大顺序 int mid=(first+end)/2; while(first<=end){ if(target<get(mountainArr,mid)) end=mid-1; else if(target==get(mountainArr,mid)) return mid; else first=mid+1; mid=(first+end)/2; } return -1; } int BiSearch_Decrease(MountainArray* mountainArr,int first,int end,int target){//从大到小顺序 int mid=(first+end)/2; while(first<=end){ if(target<get(mountainArr,mid)) first=mid+1; else if(target==get(mountainArr,mid)) return mid; else end=mid-1; mid=(first+end)/2; } return -1; } int MaxIdx(MountainArray* mountainArr,int first,int end){ int mid; while(first<end){ mid=(first+end)/2; if(get(mountainArr,mid)<get(mountainArr,mid+1)) first=mid+1; else end=mid; } return first; } int findInMountainArray(int target, MountainArray* mountainArr){ int Len=length(mountainArr),first=0,end=Len-1; int idx=MaxIdx(mountainArr,0,end); int resultL=BiSearch_Increase(mountainArr,first,idx,target); int resultR=BiSearch_Decrease(mountainArr,idx,end,target); if(resultL!=-1 && resultR!=-1) return resultL; else if(resultL!=-1 && resultR==-1) return resultL; else if(resultL==-1 && resultR!=-1) return resultR; else return -1; }