题目:
你是产品经理,目前正在带领一个团队开发新的产品。不幸的是,你的产品的最新版本没有通过质量检测。由于每个版本都是基于之前的版本开发的,所以错误的版本之后的所有版本都是错的。
假设你有 n
个版本 [1, 2, ..., n]
,你想找出导致之后所有版本出错的第一个错误的版本。
你可以通过调用 bool isBadVersion(version)
接口来判断版本号 version
是否在单元测试中出错。实现一个函数来查找第一个错误的版本。你应该尽量减少对调用 API 的次数。
示例:
给定 n = 5,并且 version = 4 是第一个错误的版本。
调用 isBadVersion(3) -> false
调用 isBadVersion(5) -> true
调用 isBadVersion(4) -> true
所以,4 是第一个错误的版本。
解答:
- 这个题可以用二分搜索解决,需要注意的是这个题要搜的实际上是第一个坏掉的版本与最后一个好的版本的中间点,实际上是搜不到的。
- 例如:对下图的版本(红色表示bad version):
- 中间点的右边全是bad version,只用找前一半[1, 4-1];
- 而如果是下图(同样红色表示bad version):
- 中间点的左边全是good version,只用找后一半[4+1, 8];
- 我们用两个指针low和high表示搜索区间,low > high时结束。由于low在后,high在前,所以low是第一个坏的版本。
代码如下:
// Forward declaration of isBadVersion API.
bool isBadVersion(int version);
class Solution {
public:
int firstBadVersion(int n) {
int low = 1;
int high = n;
while (low <= high) {
//这个地方不能直接(low + high) / 2,否则会溢出,然后循环乱掉
//也不能low / 2 + high / 2,否则第一个测试超时
int mid = low + (high - low) / 2;
if (isBadVersion(mid)) {
high = mid - 1;
}
else {
low = mid + 1;
}
}
return low;
}
};