题目描述
有序数组arr可能经过一次旋转处理,也可能没有,且arr可能存在重复的数。例如,有序数组[1,2,3,4,5,6,7],可以旋转处理成[4,5,6,7,1,2,3]等。给定一个可能旋转过的有序数组arr,返回arr中的最小值。
基本思路
利用二分查找,最坏情况为O(N)的时间复杂度。首先需要知道,如果一个有序数组经过旋转后,最小的值一定是数组中降序的那个位置,其余部分都是升序。同时,数组的第一个元素一定比最后一个元素大。如果没有经过旋转,数组整体都是升序,最小值就是数组的第一个值。
if (arr[left] < arr[right])
数组整体升序,直接返回arr[left]。
if (arr[mid] > arr[right])
降序在数组右半区,left = mid +1。
if (arr[left] > arr[mid])
降序在数组左半区,right = mid;
考虑存在的重复数字,我们去掉尾部与首部重复的数字,最坏的情况下,所有的值都是一个值。对于每个值都需要遍历一遍,所以最坏的时间复杂度是O(N)。
代码
#include <iostream>
using namespace std;
const int N = 1e7 +