总结一下二分法的情况
本篇不能完全保证正确性。如有错误,请多多指教。
普通的binary_search
#include <cstdio>
#include <cstdlib>
#include <algorithm>
using namespace std;
const int N = 10000;
int n = 10, d[N] = {0,1,1,2,2,3,5,6,7,7,10};
#define DF int l = 1, r = m, mid
#define sear_0 while(l <= r) {\
mid = l + ((r-l) >> 1);\
if(key == d[mid]) return mid;\
if(key < d[mid]) r = mid-1;\
else l = mid+1;\
}
#define sear_1 while(l <= r) {\
mid = l + ((r-l) >> 1);\
if(key <= d[mid]) r = mid-1;\
else l = mid+1;\
}
#define sear_2 while(l <= r) {\
mid = l + ((r-l) >> 1);\
if(key < d[mid]) r = mid-1;\
else l = mid+1;\
}
void pt(int a) {
printf("%d\n", a);
}
//_0 原始版 是否存在
int bin_0(int a[], int m, int key) {
DF;
sear_0
return -1;
}
//_1_1 返回大于等于key的左端点
int bin_1_1(int a[], int m, int key) {
DF;
sear_1
return l <= m ? l : -1;
}
//_1_2 返回大于key的左端点
int bin_1_2(int a[], int m, int key) {
DF;
sear_2
return l <= m ? l : -1;
}
//_2_1 返回小于等于key的右端点(由大于key的左端点得到)
int bin_2_1(int a[], int m, int key) {
DF;
sear_2
return l-1 > 0 ? l-1 : -1;
}
//_2_2 返回小于key的右端点(由大于等于key的左端点得到)
int bin_2_2(int a[], int m, int key) {
DF;
sear_1
return l-1 > 0 ? l-1 : -1;
}
//_3_1 返回等于key的左端点(由大于等于key的左端点得到)
int bin_3_1(int a[], int m, int key) {
DF;
sear_1
return (l <= m) && (a[l] == key) ? l : -1;
}
//_3_2 返回等于key的右端点(由大于key的左端点得到)
int bin_3_2(int a[], int m, int key) {
DF;
sear_2
return (l-1 > 0) && (a[l-1] == key) ? l-1 : -1;
}
int main() {
int t;
scanf("%d", &t);
pt(bin_0(d, n, t));
pt(bin_1_1(d, n, t)); pt(bin_1_2(d, n, t));
pt(bin_2_1(d, n, t)); pt(bin_2_2(d, n, t));
pt(bin_3_1(d, n, t)); pt(bin_3_2(d, n, t));
return 0;
}
有自定义判断函数的binary_search
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
using namespace std;
bool judge(int x) {} // 满足返回true,否则返回false
//最小值(下界),即满足条件的最小值 ,可据上文 "_3_1 返回等于key的左端点" 得到
//此时 judge() 的意义是大于等于下界的值都满足,小于下界的值不满足
//类比上文 key <= d[mid]
int binary_down(int left, int right) {
int mid, l = left, r = right;
while(l <= r) {
mid = l + ((r-l) >> 1);
if(judge(mid)) r = mid-1;
else l = mid+1;
}
return (l <= right) && (judge(l)) ? l : -1;
}
//最大值(上界),即满足条件的最大值 ,可据上文 "_3_2 返回等于key的右端点" 得到
//此时 judge() 的意义是小于等于下界的值都满足,大于下界的值不满足
//类比上文 !(key < d[mid]) , 即 key >= d[mid]
int binary_up(int left, int right) {
int mid, l = left, r = right;
while(l <= r) {
mid = l + ((r-l) >> 1);
if(!judge(mid)) r = mid-1;
else l = mid+1;
}
return (l-1 >= left) && (judge(l-1)) ? l-1 : -1;
}