Binary Search - 2 各式模板
前面有介紹了 Binary Search 的通用模板,但通用模板還是有缺點,就是要找的目標須在 array 範圍內,這樣才能定義 index。但很多時候題目並不會有一個準確的 array 被定義,還是需要了解各個模板才能比較好的去解答各式題目。
模板
找一個準確值
- 初始 index : l = 0, r = arr.length -1
- 循環條件: l <= r
- 縮減空間: l = mid + 1 , r = mid - 1
找一個模糊值
- 初始 index : l = 0, r = arr.length -1
- 循環條件: l < r
- 縮減空間:
- l = mid , r = mid - 1
- l = mid + 1 , r = mid
例如給定一個 arr = {1, 2, 3, 5, 5, 5, 8, 9} ,找到第一個 5 的 index
// 通用型解法
int[] nums = {1, 2, 3, 5, 5, 5, 8, 9};
int l = -1;
int r = nums.length;
while(l + 1 < r) {
int mid = l + (r - l) / 2;
if ( nums[mid] < 5 ) {
l = mid;
} else {
r = mid;
}
}
// r and l 要返回哪個呢? 要返回 r
// 因為 nums[mid] < 5
// 所以 最後 l 的位置會是 "最後一個小於5" 的 index,r 才會是答案
System.out.println("find first 5 index: " + r); //find first 5 index: 3
// 模糊值解法
// 循環條件: l < r
// 假如 arr = {5, 6} , 經過循環則 l 和 r 都會在 5 上,若 l <= r 會死循環。
//
// 縮減空間: l = mid + 1 , r = mid
// 不能是 r = mid - 1 ,因為可能會排除答案
int[] nums = {1, 2, 3, 5, 5, 5, 8, 9};
int l = 0;
int r = nums.length;
while(l < r) {
int mid = l + (r - l) / 2;
if ( nums[mid] < 5 ) {
l = mid + 1;
} else {
r = mid;
}
}
System.out.println("find first 5 index: " + r); //find first 5 index: 3
給定一個 arr = {1, 2, 3, 5, 5, 5, 8, 9} 找到最後一個 5 的 index
ans : 5
// 通用型解法
int[] nums = {1, 2, 3, 5, 5, 5, 8, 9};
int l = -1;
int r = nums.length;
while(l + 1 < r) {
int mid = l + (r - l) / 2;
if ( nums[mid] <= 5 ) {
l = mid;
} else {
r = mid;
}
}
// r and l 要返回哪個呢? 要返回 l
// 因為 nums[mid] <= 5
// 所以最後 l 的位置會是 "最後一個5" 的 index
System.out.println("find last 5 index: " + l); //find last 5 index: 5
// 模糊值解法
// 循環條件: l < r
// 假如 arr = {5, 6} , 經過循環則 l 和 r 都會在 5 上,若 l <= r 會死循環。
//
// 縮減空間: l = mid , r = mid - 1
// 不能是 l = mid + 1 ,因為可能會排除答案
int[] nums = {1, 2, 3, 5, 5, 5, 8, 9};
int l = -1;
int r = nums.length;
while(l < r) {
int mid = l + (r - l) / 2;
if ( nums[mid] <= 5 ) {
l = mid;
} else {
r = mid - 1;
}
}
System.out.println("find last 5 index: " + l); // find last 5 index: 5