443 字
2 分钟
学习笔记-3-二分

二分查找#

具体思路为每次查找时,将范围折半,判断查找数的位置并将其折半,重复以上操作就可快速得出答案。注意操作时必须保证数组是有序的!!

时间复杂度#

二分的最坏复杂度为 O(logN)O(log N)

实现#

手写#

模板1#

//往左找答案
while(l<r){
int mid=l+r>>1;//(l+r)/2
if(check(mid)){
r=mid;
}
else{
l=mid+1;
}
}

模板2#

//往右找答案
while(l<r){
int mid=l+r+1>>1;//(l+r+1)/2
if(check(mid)){
l=mid;
}
else{
r=mid-1;
}
}

模板3(浮点)#

while(r-l<1e-5){//注意所有类型都为double
double mid=(l+r)/2;
if(check(mid)){
l=mid;
}
else{
r=mid;
}
}

STL函数#

查找首个不小于给定值的元素:lower_bound

使用时直接调用lower_bound( ForwardIt first, ForwardIt last, const T& value );使用时必须保证数组有序

如果没有找到,返回last

查找首个大于给定值的元素: upper_bound

使用时直接调用upper_bound( ForwardIt first, ForwardIt last, const T& value );使用时必须保证数组有序

如果没有找到,返回last

例题#

P2249

P1102

P1163//浮点二分

二分答案#

在题目的答案有一个很大的区间,且保证这个区间对题目中的某一个量具有单调性,就可以使用二分答案来解决问题。

形式化的来说,一道题目如果符合以下条件就可以使用二分答案来求解。

  • 答案在一个区间。
  • 直接搜索不容易,但是可以容易判断一个答案是否符合条件。
  • 这个区间具有单调性,会随着一个条件的改变而变化。
  • 可能会有最大值最小化(或者最小值最大化),等典型特征。
  • check()函数要写正确,一般可以用答案带进去试。
  • 注意一些特殊的情况,写好特判。

例题#

P1873

P1024

P2240

P2678

P1182

P1824

P3853

P3743

学习笔记-3-二分
https://blog.introl.top/posts/学习笔记-3-二分/
作者
Introl
发布于
2024-03-25
许可协议
CC BY-NC-SA 4.0