- 求a的下界即求第一个大于等于a的值的位置i,即nums[i]>=a && nums[i-1]<a
- 使用二分法,伪代码如下
lower_bound(nums, l, r, a):
if(l > r) 不存在
mid = (l+r) >> 1
if(nums[mid] < a) 在右边寻找
否则,中间值是最左值,中间值即所求
否则,中间值前一个值小于a,中间值即所求
否则,在左边寻找
#include <iostream>
#include <vector>
using namespace std;
int lower_bound(vector<int> nums, int l, int r, int a) {
if(l > r) return -1;
int mid = (l+r) >> 1;
if(nums[mid] < a) return lower_bound(nums, mid+1, r, a);
if(mid == l) return l;
if(nums[mid-1] < a) return mid;
return lower_bound(nums, l, mid-1, a);
}
int main(int argc, char** argv) {
if(argc != 2) {
cout << "usage: " << argv[0] << " num\n";
return 0;
}
vector<int> v{3,4,5,5,6,6,8,10,10,14,17,17,20};
int n = v.size();
int a = stoi(argv[1]);
cout << lower_bound(v, 0, n-1, a) << endl;
return 0;
}
- 上界类似下界,是求最后一个小于等于的值,读者可以先自己尝试
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
int upper_bound(vector<int> nums, int l, int r, int a) {
if(l > r) return -1;
int mid = (l+r) >> 1;
if(nums[mid] > a) return upper_bound(nums, l, mid-1, a);
if(mid == r) return mid;
if(nums[mid+1] > a) return mid;
return upper_bound(nums, mid+1, r, a);
}