【LeetCode刷题】专题三:二分查找模板

简介: 【LeetCode刷题】专题三:二分查找模板

专题三:二分查找模板:

根据题干分析,根据二分性,划分区间,得出二分最重要的几个要点:

  1. 判断条件:while(......) 是left<=right 还是left
  2. 求中点的方式:mid = left + (right-left)/2 还是 mid = left + (right-left+1)/2这个点很关键。如果和下面mid的迭代不相符,这便是第二个死循环的点。
  3. left和right的迭代:是left = mid还是left = mid+1、是right = mid还是right = mid -1这都是需要清除的问题。

1. 朴素二分模板:

while (left <= right)
{
  int mid = left + (right - left) / 2;
  if (......)
    right = mid - 1;
  else if (......)
    left = mid + 1;
  else
    return mid;
}

2. 区间左值模板:

特点: 左值:左动,下有+1上不加;

while(left<right)
{
  int mid=left+(right-left)/2;
  if(...) left=mid+1;
  else right=mid;
}

3. 区间右值模板:

特点: 右值:右动,下有-1上+1;

while(left<right)
{
  int mid=left+(right-left+1)/2;
  if(...) right=mid-1;
  else left=mid;
}


题目1:704. 二分查找

思路分析:


思路1:朴素二分查找O(logN)

代码实现:

class Solution {
public:
    int search(vector<int>& nums, int target) {
        int left = 0, right = nums.size() - 1;
        while (left <= right) {
            int mid = left + (right - left) / 2;
            if (nums[mid] > target)
                right = mid - 1;
            else if (nums[mid] < target)
                left = mid + 1;
            else
                return mid;
        }
        return -1;
    }
};


LeetCode链接:704. 二分查找


题目2:34. 在排序数组中查找元素的第一个和最后一个位置

思路分析:

本题请看代码注释:主要三个点:判断条件、mid取值、left和right迭代

思路1:区间左右值二分查找 O(logN)

代码实现

class Solution {
public:
    vector<int> searchRange(vector<int>& nums, int target) {
        int left=0,right=nums.size()-1;
        int begin=-1,end=-1;    
        if(nums.empty()) return {-1,-1}; 
        //1.区间左端点查找: 二分区间:[小于目标值][大于等于目标值] left维护前者,right维护后置,目标值在right区间左端取到。
        while(left<right)   //判断:为什么不能等于,因为最终结果是left=right处取到,=就死循环
        {
            int mid=left+(right-left)/2;  //当还剩最后left和right相邻时,指向左端点,结合迭代,左端点可以跳出来,右端点不能。
            if(nums[mid]>=target) right=mid;  //right不跳出区间,因为可能目标值就是right处
            else left=mid+1;          //left需要移动,因为目标值一定不在它的区间
        }
        if(target==nums[left])  begin=left;
        //2.区间左端点查找:  
        right=nums.size()-1;  //注意更新left和right,优化:右端点一定在左端点后,所以left可以不更新,就处于左端点处
        while(left<right)
        {
            int mid=left+(right-left+1)/2;  
            if(nums[mid]>target) right=mid-1;
            else left=mid;
        }
        if(target==nums[left])    end=left;
        
        return {begin,end};
    }
};

LeetCode刷题:34.在排序数组中查找元素的第一个和最后一个位置

相关文章
|
4天前
|
Unix Shell Linux
LeetCode刷题 Shell编程四则 | 194. 转置文件 192. 统计词频 193. 有效电话号码 195. 第十行
本文提供了几个Linux shell脚本编程问题的解决方案,包括转置文件内容、统计词频、验证有效电话号码和提取文件的第十行,每个问题都给出了至少一种实现方法。
LeetCode刷题 Shell编程四则 | 194. 转置文件 192. 统计词频 193. 有效电话号码 195. 第十行
|
2月前
|
搜索推荐 索引 Python
【Leetcode刷题Python】牛客. 数组中未出现的最小正整数
本文介绍了牛客网题目"数组中未出现的最小正整数"的解法,提供了一种满足O(n)时间复杂度和O(1)空间复杂度要求的原地排序算法,并给出了Python实现代码。
82 2
|
4天前
|
数据采集 负载均衡 安全
LeetCode刷题 多线程编程九则 | 1188. 设计有限阻塞队列 1242. 多线程网页爬虫 1279. 红绿灯路口
本文提供了多个多线程编程问题的解决方案,包括设计有限阻塞队列、多线程网页爬虫、红绿灯路口等,每个问题都给出了至少一种实现方法,涵盖了互斥锁、条件变量、信号量等线程同步机制的使用。
LeetCode刷题 多线程编程九则 | 1188. 设计有限阻塞队列 1242. 多线程网页爬虫 1279. 红绿灯路口
|
2月前
|
算法 Python
【Leetcode刷题Python】 LeetCode 2038. 如果相邻两个颜色均相同则删除当前颜色
本文介绍了LeetCode 2038题的解法,题目要求在一个由'A'和'B'组成的字符串中,按照特定规则轮流删除颜色片段,判断Alice是否能够获胜,并提供了Python的实现代码。
39 3
|
2月前
|
算法 Python
【Leetcode刷题Python】剑指 Offer 33. 二叉搜索树的后序遍历序列
本文提供了一种Python算法,用以判断给定整数数组是否为某二叉搜索树的后序遍历结果,通过识别根节点并递归验证左右子树的值是否满足二叉搜索树的性质。
17 3
|
2月前
|
Python
【Leetcode刷题Python】50. Pow(x, n)
本文介绍了LeetCode第50题"Pow(x, n)"的解法,题目要求实现计算x的n次幂的函数,文章提供了递归分治法的详细解析和Python实现代码。
18 1
|
2月前
|
Python
【Leetcode刷题Python】LeetCode 478. 在圆内随机生成点
本文介绍了LeetCode 478题的解法,题目要求在给定圆的半径和圆心位置的情况下实现在圆内均匀随机生成点的功能,并提供了Python的实现代码。
20 1
|
2月前
|
算法 Python
【Leetcode刷题Python】295. 数据流的中位数
本文介绍了一种使用Python实现的数据结构,用以支持数据流中添加整数并返回当前所有元素的中位数,通过排序列表来计算中位数。
16 1
|
2月前
|
算法 Python
【Leetcode刷题Python】73. 矩阵置零
本文介绍了LeetCode第73题的解法,题目要求在给定矩阵中将所有值为0的元素所在的行和列全部置为0,并提供了一种原地算法的Python实现。
19 0
【Leetcode刷题Python】73. 矩阵置零
|
2月前
|
Python
【Leetcode刷题Python】1467. 两个盒子中球的颜色数相同的概率
本文介绍了LeetCode第50题"Pow(x, n)"的解法,题目要求实现计算x的n次幂的函数,文章提供了递归分治法的详细解析和Python实现代码。
24 0