Find Minimum in Rotated Sorted Array


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

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

Find the minimum element.

You may assume no duplicate exists in the array.

SOLUTION 1:
这个题目trick的地方在于,它的旋转pivot次数未知。所以有可能它转了一圈又转回了原处

所以我们代码要处理2种情况:
我们还是用二分法来做。比起全部扫一次,二分法可以做到LogN的复杂度。
1. Sorted

这种情况简单,先计算出mid的值,如果它处在左右的中间,证明这个数列是正常的sorted,直接返回左边。

2. 中间断开(也就是说旋转过)
我们的目的是要找出存在断口的地方。所以我们可以每次求一下mid的值,把mid
跟左边比一下,如果是正常序,就丢掉左边,反之丢掉右边,不断反复直到找到断口。
分析一下:
比如4 5 6 7 0 1 2  从中间断开后,它是由一个有序跟一个无序的序列组成的。
如果left = 0, right = 6,mid = 3, 那么4, 5, 6, 7 是正序, 7, 0, 1,
2是逆序,所以我们要丢掉左边。这样反复操作,直到数列中只有2个数字,就是断开处,这题我们会得到7,0,返回后一个就可以了。

以下图示简单描述了通过三步操作逐步逼近断口处。每一次我们可以扔掉一半,速度是LogN.

注意,丢掉半边时,mid不可以丢掉,因为有可能mid就是答案。
例子: 3, 1, 2 的时候,3, 1是逆序,1, 2是正序,如果你扔掉1,2你就丢掉了答案。

 // Solution 1:
public int findMin1(int[] num) {
if (num == null || num.length == 0) {
return 0;
} if (num.length == 1) {
return num[0];
} // 至少有2个元素,才有讨论的价值
int l = 0;
int r = num.length - 1; while (l < r) {
int mid = l + (r - l)/2;
// Means that there is no rotate.
if (num[mid] >= num[l] && num[mid] <= num[r]) {
return num[0];
} // rotate > 0的情况
if (l == r - 1) {
// 当只余下2个元素的时候,这里是断点,右边的是小值
return num[r];
} if (num[mid] >= num[l]) {
// The left side is sorted. Discard left.
l = mid;
} else {
// The right side is sorted.
r = mid;
}
} return 0;
}

SOLUTION 2:

采用九章算法的二分法模板来解:

这个模板最大的好处是 while(left < right - 1) 这样的话,终止时就一定是left = right - 1,而且mid 一直会是在中间,不会靠到left去。判断起来会相当
便利。
常见bug:

// bug 1: should not use l = m + 1 and r = m - 1.
// this may discard the minumul value.

A example: 3, 1, 2.

 // solution 2:
public int findMin(int[] A) {
if (A == null || A.length == 0) {
return 0;
} if (A.length == 1) {
return A[0];
} else if (A.length == 2) {
return Math.min(A[0], A[1]);
} // 至少有3个元素,才有讨论的价值
int l = 0;
int r = A.length - 1; while (l < r - 1) {
int m = l + (r - l) / 2; // means that there is no rotate.
if (A[m] < A[r] && A[m] > A[l]) {
return A[0];
} // left side is sorted.
if (A[m] > A[l]) {
l = m;
} else {
r = m;
}
} return A[r];
}
 
所以以后一定要多使用模板化的编程 ,特别是这里总结的二分法模板:
         while (l < r - 1) {
int m = l + (r - l) / 2; // means that there is no rotate.
... 这里添加各种退出条件,比如找到了目标值等
// left side is sorted.
if (A[m] > A[l]) {
l = m;
} else {
r = m;
}
}

SOLUTION 3:

在解答2的基础之上,可以把判断是否rotated的statement去掉,然后每次丢弃有序数列时,先丢弃右边的。这样子即使是从未rotated的也没有关系,因为一直是丢右边的

直到余下左边最后2个。

 public int findMin(int[] num) {
if (num == null || num.length == 0) {
return 0;
} int l = 0;
int r = num.length - 1; while (l < r - 1) {
int m = l + (r - l) / 2; if (num[m] < num[r]) {
// bug 1: should not use l = m + 1 and r = m - 1.
// this may discard the minumul value.
r = m;
} else {
l = m;
}
} return Math.min(num[l], num[r]);
}

SOLUTION 4:

在解答3的基础之上先,预判断是不是旋转过,这样如果没有旋转我们可以直接把解算出即可。

 public int findMin(int[] num) {
if (num == null || num.length == ) {
return ;
} int l = ;
int r = num.length - ; if (num[l] < num[r]) {
return num[l];
} while (l < r - ) {
int m = l + (r - l) / ; if (num[m] < num[r]) {
// bug 1: should not use l = m + 1 and r = m - 1.
// this may discard the minumul value.
r = m;
} else {
l = m;
}
} return Math.min(num[l], num[r]);
}

FOLLOW UP:

LeetCode 新题: Find Minimum in Rotated Sorted Array II 解题报告-二分法模板解法

GitHub:

GitHub代码链接

LeetCode 新题: Find Minimum in Rotated Sorted Array 解题报告-二分法模板解法的更多相关文章

  1. 【LeetCode】153. Find Minimum in Rotated Sorted Array 解题报告(Python)

    [LeetCode]153. Find Minimum in Rotated Sorted Array 解题报告(Python) 标签: LeetCode 题目地址:https://leetcode. ...

  2. LeetCode 新题: Find Minimum in Rotated Sorted Array II 解题报告-二分法模板解法

    Find Minimum in Rotated Sorted Array II Follow up for "Find Minimum in Rotated Sorted Array&quo ...

  3. 【LeetCode】Find Minimum in Rotated Sorted Array 解题报告

    今天看到LeetCode OJ题目下方多了"Show Tags"功能.我觉着挺好,方便刚開始学习的人分类练习.同一时候也是解题时的思路提示. [题目] Suppose a sort ...

  4. LeetCode: Search in Rotated Sorted Array 解题报告

    Search in Rotated Sorted Array Suppose a sorted array is rotated at some pivot unknown to you before ...

  5. 【LeetCode】154. Find Minimum in Rotated Sorted Array II 解题报告(Python)

    [LeetCode]154. Find Minimum in Rotated Sorted Array II 解题报告(Python) 标签: LeetCode 题目地址:https://leetco ...

  6. 【刷题-LeetCode】154 Find Minimum in Rotated Sorted Array II

    Find Minimum in Rotated Sorted Array II Suppose an array sorted in ascending order is rotated at som ...

  7. 【刷题-LeetCode】153 Find Minimum in Rotated Sorted Array

    Find Minimum in Rotated Sorted Array Suppose an array sorted in ascending order is rotated at some p ...

  8. 【LeetCode】153. Find Minimum in Rotated Sorted Array (3 solutions)

    Find Minimum in Rotated Sorted Array Suppose a sorted array is rotated at some pivot unknown to you ...

  9. LeetCode OJ 154. Find Minimum in Rotated Sorted Array II

    Follow up for "Find Minimum in Rotated Sorted Array":What if duplicates are allowed? Would ...

随机推荐

  1. heap与stack的差

    本文内容来源于<程序猿面试宝典>第三版. 在进行C/C++编程时.常常将操作的内存分下面几个类别: 栈区(stack):由编译器自己主动分配和释放,存放函数的參数值.局部变量的值等. 其操 ...

  2. doGet和doPost区别

    1,form运行方式 当form框里面的method为get时,执行doGet方法当form框里面的method为post时,执行doPost方法 2,生成方式 get方式有四种:1)直接在URL地址 ...

  3. CSS3+JS 实现的便签应用

    概述 利用HTML5新增的 locationStorage 实现的便签应用,没有使用 JQuery,主要是为了练习原生JS的使用,采用响应式开发,在手机端和桌面端都有良好的体验,而且使用CSS3添加了 ...

  4. mysql sleep连接太多怎么办

    摘要:interactive_timeout和wait_timeout参数对sleep连接的影响 interactive_timeout 参数含义:服务器关闭交互式连接前等待活动的秒数.交互式客户端定 ...

  5. MSSQL-SQL SERVER一些使用中的技巧

    获取前一天时间"getdate() - 1" 获取上一小时时间"dateadd(hour, -1, getdate())" order by field1, f ...

  6. HDUOJ----1263水果

    水果 Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total Submissi ...

  7. HDUOJ---What Are You Talking About

    What Are You Talking About Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 102400/204800 K ...

  8. HDUOJ -----免费馅饼

    免费馅饼 Time Limit : 2000/1000ms (Java/Other)   Memory Limit : 65536/32768K (Java/Other) Total Submissi ...

  9. RabbitMQ消息队列(五):Routing 消息路由[转]

    上篇文章中,我们构建了一个简单的日志系统.接下来,我们将丰富它:能够使用不同的severity(严重程度)来监听不同等级的log.比如我们希望只有error的log才保存到磁盘上. 1. Bindin ...

  10. android自定义控件实例

    很多时候android常用的控件不能满足我们的需求,那么我们就需要自定义一个控件了.今天做了一个自定义控件的实例,来分享下. 首先定义一个layout实现按钮内部布局: 01 <?xml ver ...