[C++]LeetCode: 132 Find Minimum in Rotated Sorted Array II (

题目:

Suppose a sorted array is rotated at some pivot unknown to you beforehand.

(i.e.,0 1 2 4 5 6 7might become4 5 6 7 0 1 2).

Find the minimum element.

The array may contain duplicates.

思路:这道题是Search in Rotated Sorted Array的扩展。和Find Minimum in Rotated Sorted Array唯一的区别是,这都题目中会有重复的元素出现。在没有重复元素出现时,我们是根据边缘值和中间值比较确定,如何切掉一半元素的,如果加上了重复元素,我们无法判断哪边有序,哪边无序,也就无法确定元素之间的关系。假设原来的数组{1,2,3,3,3,3,3},旋转后得到{3,3,3,3,3,1,2}或者{3,1,2,3,3,3,3},这时我们判断时边缘和中间值都相等,我们并不知道应该截取哪一半,所以我们只能移动边缘一步,直到边缘和中间不在相等或者相遇。这就导致了最坏的情况下,可能每次都只移动一步,总共移动N次,算法的复杂度变成O(N).

这里我们还需要注意一个问题,我们利用右边缘和中间值来作比较,如果A[MID] == A[HI],我们移动HI一步,HI–. 这样最后返回A[lo]就是正确的最小值。但是如果使用左边缘来判断,由于除法的截断性,出现lo == mid, 导致A[lo] == A[mid], 如果我们移动下界lo++, 可能会跳过最小值。如数组{1,3},最后结果会返回A[lo] = 3. 上界hi就不会受到除法的截断性的影响,出现相等,就是遇到了重复元素这种情况,我们移动hi,不会影响结果。

二分查找思想并不难,可是实现过程中,需要反复考虑多种情况,主要要处理好细节。

复杂度:O(N)

Attention:

1. 移动上界,用上界来判断。

AC Code:

class Solution {public:int findMin(vector<int> &num) {int lo = 0;int hi = num.size() – 1;int mid = 0;while(lo < hi){int mid = lo + (hi – lo) / 2;if(num[hi] < num[mid]){lo = mid + 1;}else if(num[hi] > num[mid]){hi = mid;}else{hi–;}}return num[lo];}};面试中这种问题比较常见,现在的趋势是面试官从一个问题出发,然后follow up一些扩展的问题,而且这些问题一般涉及复杂度的改变,,所以是面试中的一道好题,更有可能出现,可以结合Find Minimum in Rotated Sorted Array来复习。

当爱丽思丢失了通往仙境的钥匙,

[C++]LeetCode: 132 Find Minimum in Rotated Sorted Array II (

相关文章:

你感兴趣的文章:

标签云: