【剑指offer】6.旋转数组的最小数字

题目

把一个数组最开始的若干个元素搬到数组的末尾,我们称之为数组的旋转。输入一个非递减排序的数组的一个旋转,输出旋转数组的最小元素。例如数组{3,4,5,1,2}为{1,2,3,4,5}的一个旋转,该数组的最小值为1。NOTE:给出的所有元素都大于0,若数组大小为0,请返回0。


分析

题目给出了输入的数组为非递减数组的一个旋转,那么旋转数组在一定程度上是有序的。因此盖提可以使用二分查找来加快搜索速度,而非使用遍历数组寻找最小值。思路如下:

  1. 指定 l o w low low h i g h high high两个指针,分别指向数组 a r r a y array array的第一个元素和最后一个元素。 m i d = ( l o w + h i g h ) / 2 mid = (low+high)/2 mid=(low+high)/2
  2. a r r a y [ m i d ] ⩾ a r r a y [ l o w ] array[mid] \geqslant array[low] array[mid]array[low],则最小值在 m i d mid mid h i g h high high之间,赋值 l o w = m i d low=mid low=mid
  3. 反之若 a r r a y [ m i d ] ⩽ a r r a y [ h i g h ] array[mid] \leqslant array[high] array[mid]array[high],则最小值在 l o w low low m i d mid mid之间,赋值 h i g h = m i d high=mid high=mid,若 h i g h − l o w = = 1 high-low==1 highlow==1则返回 a r r a y [ l o w ] array[low] array[low] a r r a y [ h i g h ] array[high] array[high]之间的最小值;
  4. 但是还需注意到 a r r a y [ h i g h ] = = a r r a y [ l o w ] = = a r r a y [ m i d ] array[high] == array[low] == array[mid] array[high]==array[low]==array[mid]的这种情况,这种情况下无法判断二分查找下一步该怎么走,那么只能使用遍历 l o w low low h i g h high high的所有元素查找最小值并将其返回即可。

github链接如下:JZ06-旋转数组的最小数字


C++代码

#include <iostream>
#include <vector>
using namespace std; 

class Solution {
	public:
	    int minNumberInRotateArray(vector<int> rotateArray) {
	    	if (rotateArray.size() == 0){
	    		return 0;
			}
			int low = 0;
			int high = rotateArray.size() - 1;
			int mid = (low + high) / 2;
			while(rotateArray[low] >= rotateArray[high]){
				if(high - low ==1){
					mid = high;
					break;
				}
				mid = (low + high) / 2;
				if (rotateArray[low] == rotateArray[high] && rotateArray[low] == rotateArray[mid]){
					return this->findMin(rotateArray,low,high);
				}
				if (rotateArray[mid] >= rotateArray[low]){
					low = mid;
				}else if(rotateArray[mid] <= rotateArray[high]){
					high = mid;
				}
			}
			return rotateArray[mid];
	    }
	    
	    int findMin(vector<int> rotateArray,int low,int high){
	    	int min = rotateArray[low];
	    	for(int i = low + 1; i < high ; i++){
	    		if(rotateArray[i] < min){
	    			min = rotateArray[i];
				}
			}
			return min;
		}
};


int main(){
	
	int size;
	cin >> size;
	vector<int> array(size);
	for(int i = 0 ; i < size ; i++){
		cin>>array[i];
	}
	
	Solution s;
	cout<<s.minNumberInRotateArray(array);
	
	return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

daipuweiai

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值