题目描述:
你是产品经理,目前正在带领一个团队开发新的产品。不幸的是,你的产品的最新版本没有通过质量检测。由于每个版本都是基于之前的版本开发的,所以错误的版本之后的所有版本都是错的。
假设你有 n 个版本 [1, 2, …, n],你想找出导致之后所有版本出错的第一个错误的版本。
你可以通过调用 bool isBadVersion(version) 接口来判断版本号 version 是否在单元测试中出错。实现一个函数来查找第一个错误的版本。你应该尽量减少对调用 API 的次数。
示例1:
输入: n = 5, bad = 4
输出: 4
解释: 调用 isBadVersion(3) -> false
调用 isBadVersion(5) -> true
调用 isBadVersion(4) -> true
所以,4 是第一个错误的版本。
示例2:
输入: n = 1, bad = 1
输出: 1
提示:
- 1 <= bad <= n <= 231 - 1
思路:
这是一道应用题,由题目可知版本号是从1开始依次递增1的有序数组,所以可以应用于排序完毕的数组的算法都可以,由于上一篇题目是二分法基础,那这次我们肯定优先考虑二分法来处理这个题
误区:
在思考题解的过程中,我们要知道这和单纯的二分法找数不同,因为我们是无法直接得知中间数是否是我们要找的第一个错误版本,第一个的右边都是错的 左边都是对的,我们只能知道这个版本是对的还是错的,所以我们的搜索条件应该是当「右边界和左边界重合时」才能找到那个答案,所以我们在循环时不能用left<=right 而应该用left<right
题解:
public int firstBadVersion(int n) {
//如上一篇二分法相同,定义一个「窗口」,左边界是版本号1,所以left=1,而右边界为最新版本 n
int left=1,mid=0;
//不加等号是因为
//其他如二分法相同
while(left<n){
mid = (n-left)/2 +left;
if(isBadVersion(mid)==false){
left = mid +1;
}else{
n = mid;
}
}
return left;
}