题意:有一个长度为 n 的非降序数组,将它进行旋转,即把一个数组最开始的若干个元素搬到数组的末尾,变成一个旋转数组。问,给定这样一个旋转数组,求数组中的最小值。
方法一:
直接遍历
思路:因为原数组是非降序数组,又把一个数组最开始的若干个元素搬到数组的末尾,那么数组的最大值一定与最小值相邻。
for一遍,查找如果前面的值大于后面的值,则说明后面的这个值是最小值。
class Solution { public: int minNumberInRotateArray(vector<int> rotateArray) { int n=rotateArray.size(); for(int i=1;i<n;i++){//for循环 if(rotateArray[i-1]>rotateArray[i])//如果前面的值大于后面的值,则说明后面的这个值是最小值 return rotateArray[i]; } return rotateArray[0]; } };
时间复杂度:
空间复杂度:
方法二:
二分
思路:利用二分算法 维持一段递增的区间(即比较中间值和左右边界值)。
如果中间值大于左边界值,则通过来缩小范围;如果中间值小于等于左边界并且小于右边界,则来缩小范围;如果都不满足,则通过来缩小范围。
特殊情况:如果左边界值小于右边界值,说明已成功。
class Solution { public: int minNumberInRotateArray(vector<int> rotateArray) { int n=rotateArray.size(); int l=0,r=n-1,mid;//初始化左右边界 while(l<r){ if(rotateArray[l]<rotateArray[r])//特殊情况:如果左边界小于右边界,返回左边界的值 return rotateArray[l]; mid=(l+r)/2;//二分 if(rotateArray[mid]>rotateArray[l]){//如果大于左边界,则l=mid+1 l=mid+1; }else if(rotateArray[mid]<rotateArray[r]){//如果小于等于左边界并且小于右边界,则r=mid r=mid; }else{//如果都不是,则缩小范围,l++ l++; } } return rotateArray[l]; } };
时间复杂度:空间复杂度: