while(l != r){
int mid =(l + r)/2;if(wm[mid].num >= target){
r = mid;// 右边可能}else{
l = mid +1;// 左边肯定不是}}// 输出 l r 位置均可
390 原木切割,尽可能大, 1100 问题
// func 通过计算以改长度切割是否满足段数要求int l =1, r = lr;// 确定左右边界,1 - 最短原木长while(l != r){
int mid =(l + r +1)/2;// 原木切割数量足够if(func(mid)>= m){
l = mid;// 左边可能}else{
r = mid -1;// 右边拒绝}}// return l r 均可
393 切绳子,尽可能长,1100 问题
// func 通过计算以改长度切割是否满足段数要求double l =0, r = lr;// 确定左右// 小数通过精度判断while(l - r >0.00001){
double mid =(l + r +1)/2;if(func(mid)>= m){
l = mid;}else{
r = mid -1;}}
82 伐木,据木材但尽可能多,1100 问题
// func 通过计算以改长度切割是否满足段数要求int l =0, r = tr;// 确定左右,右点选最长的while(l != r){
int mid =(l + r +1)/2;if(func(mid)>= m){
l = mid;}else{
r = mid -1;}}
391 数列分段,和尽可能小,0011 问题
// func 计算是否符合分段数intfunc(int x){
int cnt =0, now =0;for(...){
// 分段和计数逻辑if(now + num[i]== x){
cnt++;
now =0;}elseif(now + num[i]> x){
cnt++;
now = num[i];}else{
now += num[i];}}if(now) cnt++;return cnt;}int l = tl, r = tr;// 左为单最大元素,右为元素和while(l != r){
int mid =(l + r)/2;if(func(mid)>= m){
r = mid;}else{
l = mid +1;}}...
394 跳石头,最近的尽可能远,1100 问题
// func 输入间距确认移走石头数intfunc(int d){
int cnt =0, last =0;for(...){
// 小于最小间距的石头要移走if(num[i]- last < d){
cnt++;}else{
last = num[i];}}return cnt;}int l = tl, r = ll;// 左为最小的间距,右为起始石头到结束石头的间距while(l != r){
int mid =(l + r +1)/2;if(func(mid)<= m){
l = mid;}else{
r = mid -1;}}...
392 丢瓶盖,最近的尽可能远,1100 问题
// func 根据距离返回丢瓶盖书intfunc(int d){
int s =0, last = num[0];for(...){
if(last - num[i]>= d){
s++;
last = num[i];}}return s;}int l =1, r = tr;// 距离为从 1 到最大坐标while(l != r){
int mid =(l + r +1)/2;if(func(mid)>= m){
l = mid;}else{
r = mid -1;}}
395 复制书稿,时间尽可能短,0011 问题
// func 根据时间返回抄写书稿的人数intfunc(int x){
int cnt =0, now =0;for(int i =0; i < m;++i){
if(now + num[i]== x){
cnt++;
now =0;}elseif(now + num[i]> x){
cnt++;
now = num[i];}else{
now += num[i];}}if(now){
cnt++;}return cnt;}int l = tl, r = tr;// 左为最长抄书人的时间,右为抄书总时间while(l != r){
int mid =(l + r)/2;if(func(mid)<= k)[
r = mid;}else{
l = mid +1;}}...
244 正方形围栏大小,满足条件最小的,0011 问题
// 在 l r 范围内查找,找到一个长度正好符合 x 方向和 y 方向上的围栏条件// 在选好的 x 轴后的 y 轴上判定数量boolcheck_y(int s,int e,int l){
int cnt =0;for(int i = s; i <= e;++i){
tmp[cnt++]= arr[i].y;}sort(tmp, tmp + cnt);// 满足数量大于等于 cfor(int i = c -1; i < cnt;++i){
if(tmp[i]- tmp[i - c +1]< l)return1;}return0;}// 先看 x 轴上在该长度是否满足数量要求,再看 y 轴,都满足符合要求boolcheck(int l){
int j =0;for(int i =0; i < n;++i){
while(arr[i].x - arr[j].x >= l)++j;if(i - j +1< c)return0;while(check_y(j, i))return1;}return0;}intbs(int l,int r){
if(l == r)return l;int mid =(l + r)/2;// 如果该长度正方形满足容纳,正方形可以再小,直到找到一个可以满足最小的容纳if(check(mid))returnbs(l, mid);// 不满足容纳,可以再大returnbs(mid +1, r);}