算法学习笔记——二分搜索

二分搜索

在有序数组中确定num存在还是不存在:

  • arr[m] == num,则num存在
  • arr[m] > num,则 r = m - 1,缩小r的范围,继续往左二分
  • arr[m] < num,则l = m + 1,缩小l的范围,继续往右二分
// 保证arr有序,才能用这个方法
public static boolen exist(int[] arr, int num) {if (arr == null || arr.length == 0){return false;}int l = 0, r = arr.length - 1, m = 0;while (l <= r) {// 中间值m = l + ((r - l) >> 1);if (arr[m] == num) {// 中间值 == num,直接返回结果return true;} else if (arr[m] > num) {// 中间值 > num,缩小r的范围r = m - 1;} else {// 中间值 < num, 缩小l的范围l = m + 1;}}return false;
}

有序数组中找>=num的最左位置:

  • ans(二分搜索法答案) 初始值设置为:-1,-1表示不存在符合要求的值
  • middle(中点值) >= num 时修改ans = middle 并 r = middle - 1 缩小右边范围,继续往左二分
  • middle(中点值) < num 时 不修改 ans 但 l = middle + 1 缩小左边范围 ,继续往右二分
  • 求中间值公式用:l + ((r - l) >> 1) 或者 l + ((r - 1) / 2),防止运算数值溢出
  • 找<=num的最左位置没有意义,直接找下标为0的位置进行判断就可以得出结果
// 保证arr有序,才能用这个方法
// 有序数组中找>=num的最左位置
public static int findLeft(int[] arr, int num) {int l = 0, r = arr.length - 1, m = 0;int ans = -1;while (l <= r){m = l + ((r - l) >> 1); // 等于 l + ((r - 1) / 2), 等于 (l + r) / 2if (arr[m] >= num) {ans = m;r = m - 1;} else {l = m + 1;}}return ans;
}

在有序数组中找<=num的最右位置:

  • ans(二分搜索法答案) 初始值设置为:-1,-1表示不存在符合要求的值
  • middle(中点值) <= num 时修改ans = middle 并 l = middle + 1 缩小右边范围,继续往右二分
  • middle(中点值) > num 时 不修改 ans 但 r = middle - 1 缩小左边范围 ,继续往左二分
  • 求中间值公式用:l + ((r - l) >> 1) 或者 l + ((r - 1) / 2),防止运算数值溢出
// 保证arr有序,才能用这个方法
// 有序数组中找<=num的最右位置
public static int findLeft(int[] arr, int num) {int l = 0, r = arr.length - 1, m = 0;int ans = -1;while (l <= r){m = l + ((r - l) >> 1); // 等于 l + ((r - 1) / 2), 等于 (l + r) / 2if (arr[m] <= num) {ans = m;l = m + 1;} else {r = m - 1;}}return ans;
}

二分搜索不一定发生在有序数组上(比如寻找峰值问题):

  • 峰值:i-1 < i > i+1,则i为峰值,如果右边或者左边没数值可以认为是无穷小

  • 数组条件:数组中相邻的两个数不相等, 只返回一个峰值就行

  • 0位置不是峰值,N-1位置不是峰值,则呈现左边上扬右边下降的趋势,这中间会出现一个或者多个峰值

  • 计算步骤:

    1. 先判断数组[0]是不是峰值,是则直接返回
    2. 再判断数组[N-1]是不是峰值,是则直接返回
    3. 设置 L = 1,R = N-2,求中间值,如果中间值是峰值则直接返回
    4. 判断中间值的大小,当左侧数值>中间值,往左侧二分,而右侧数值>中间值,往右侧二分,如果两个都成立选其中一个就行
    // 峰值元素是指其严格大于左右相邻值的元素
    // 给你一个整数数组 nums,已知任何两个相邻的值都不相等
    // 找到峰值元素并返回其索引
    // 数组可能包含多个峰值,在这种情况下,返回任何一个峰值 所在位置即可
    // 你可以假设 nums[-1] = nums[n] = 无穷小
    // 你必须实现时间复杂度为 0(log n) 的算法来解决此问题
    public static int findPeakElement(int[] arr) {int n = arr.length;// 小   小// -1 0 1if (arr.length == 1) {return 0;}// 数组长度 >= 2// 单独验证0位置,是不是峰值点if (arr[0] > arr[1]) {return 0;}//  单独验证n-1位置,是不是峰值点if (arr[n - 1] > arr[n - 2]) {return n - 1;}// X   中间一定有一个峰值    X// 0                      N-1// 中间 :1 ~ n-2 ,一定有峰值点// 每一步的l...r : 一定有峰值点int l = 1, r = n - 2, m = 0, ans = -1;while (l <= r) {m = l + ((r - l) >> 1);if (arr[m - 1] > arr[m]) {r = m - 1;} else if (arr[m] < arr[m + 1]) {l = m + 1;} else {ans = m;break;}}return ans;
    }
    

某侧必有对应的值或者某侧必没有对应的值,则可以使用二分搜索法

如果数组长度为n,那么二分搜索搜索次数是log n次,以2为底

二分搜索世界复杂度o(log n)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/24700.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Android基础-进程间通信

在Android系统中&#xff0c;跨进程通信&#xff08;IPC&#xff0c;Inter-Process Communication&#xff09;是实现不同应用程序或同一应用程序中不同进程间数据共享和交互的关键技术。Android提供了多种IPC机制&#xff0c;每种机制都有其特定的使用场景和优缺点。下面将详细…

代码随想录算法训练营第36期DAY51

DAY51 121买卖股票的最佳时机 做过了。算是二刷&#xff1a;来自力扣优质题解 贪心&#xff1a; 每次记录更新最小点和最大出售值。 class Solution {public: int maxProfit(vector<int>& prices) { int cur,resINT_MIN,curminINT_MAX; for(int…

从军事角度理解“战略与战术”

战略与战术&#xff0c;均源于军事术语。 战略&#xff08;Strategy&#xff09;&#xff0c;源自希腊语词汇“strategos&#xff08;将军&#xff09;”和“strategia&#xff08;军事指挥部&#xff0c;即将军的办公室和技能&#xff09;”。指的是指挥全局性作战规划的谋略…

【位运算】【前缀和】个人练习-Leetcode-1177. Can Make Palindrome from Substring

题目链接&#xff1a;https://leetcode.cn/problems/can-make-palindrome-from-substring/description/ 题目大意&#xff1a;给出一个字符串s&#xff0c;每次query给出l, r, k&#xff0c;要求判断子串s[l:r1]在经过k次操作后是否能变为回文串。一次操作可以将子串内的一个字…

mysql 数据库在liunx 上的备份和恢复

一. mysql 数据库备份 sh 脚本 1. vim sqlback.sh #!/bin/bashUSER"root" #账号 PASSWORD"123456" #密码 DATABASE"test" #数据库名 BACKUP_DIR"/home/dev/mysql" #备份存的目录 TIMESTAMP$(date "%F") …

搭建python虚拟环境,并在VSCode中使用

创建环境 python -m venv E:\python\flask\venv激活环境 运行下图所示的bat文件 退出环境 执行下面的语句 deactivateVSCode中配置&#xff1a; ①使用CTRLshiftp命令&#xff0c;使用CTRLshiftp命令&#xff0c;输入&#xff1a; Python: Select Interpreter②选择之前创建…

【计算视觉】学习计算机视觉你不得不膜拜的CVPR大神:何凯明

目录 第一章&#xff1a;CVPR——计算机视觉的终极擂台 第二章&#xff1a;何凯明——计算机视觉领域的耀眼星辰 第三章&#xff1a;高引用论文——计算机视觉研究的璀璨星辰 第四章&#xff1a;何凯明的CVPR论文——深度学习的探索之旅 第五章&#xff1a;结语——向何凯…

翻译《The Old New Thing》- Why isn’t there a SendThreadMessage function?

Why isnt there a SendThreadMessage function? - The Old New Thing (microsoft.com)https://devblogs.microsoft.com/oldnewthing/20081223-00/?p19743 Raymond Chen 2008年12月23日 为什么没有 SendThreadMessage 函数&#xff1f; 简要 文章讨论了 Windows 中不存在 Sen…

WHAT - 发布订阅

目录 一、常见实现方案1.1 使用事件发射器&#xff08;Event Emitter&#xff09;1.2 自定义事件系统&#xff08;EventBus&#xff09;1.3 使用库如 PubSubJS1.4 使用框架内置的状态管理工具Vue.jsReact (使用 Context API 或 Redux) 二、先后关系2.1 缓存事件数据2.2 使用 Re…

React hooks动态配置侧边栏

React hooks根据不同需求 还有不同的角色 动态的去配置侧边栏 需求&#xff1a; 点击某个按钮是一套侧边栏 &#xff0c;不同角色&#xff08;比如管理员之类的权限高一点&#xff09;比普通用户多个侧边栏 然后点击另一个按钮是另一套侧边栏 此时&#xff0c;就需要动态的去…

【React】classnames 优化类名控制

1. 介绍 classnames是一个简单的JS库&#xff0c;可以非常方便的通过条件动态的控制class类名的显示 ClassNames是一个用于有条件处理classname字符串连接的库 简单来说就是动态地去操作类名&#xff0c;把符合条件的类名粘在一起 现在的问题&#xff1a;字符串的拼接方式不…

KMeans聚类分析星

1. datasample initial_centroids datasample(data, k, Replace, false); 是MATLAB中的命令&#xff0c;用于从数据集data中随机抽取k个样本作为初始聚类汇总新&#xff0c;并且抽取时不放回。 datasample&#xff1a;是MATLAB中的函数&#xff0c;用于从数组中随机抽取样本d…

halcon算子之prepare_object_model_3d详解

为某一操作准备三维对象模型。 Description 操作符prepare_object_model_3d准备3D对象模型ObjectModel3D,用于下面目的中给出的操作。它计算操作所需的值并将其存储在ObjectModel3D中,从而加快了后续操作。没有必要调用prepare_object_model_3d。但是,如果要多次使用3D对象…

5、js关于数组的常用方法(19种)

一、改变原数组的方法 1.push&#xff08;&#xff09; 末尾添加数据 语法&#xff1a; arr.push(要插入的数据可以多个) // push 尾部添加数据const arr [1,2,3,4,5];arr.push(6,7);console.log(arr);//(7) [1, 2, 3, 4, 5, 6, 7]2. pop&#xff08;&#xff09; 末尾删除一…

大疆智图_空三二维重建成果传输

一、软件环境 1.1 所需软件 1、 大疆智图&#xff1a;点击下载&#xff1b;   2、 ArcGIS Pro 3.1.5&#xff1a;点击下载&#xff0c;建议使用IDM或Aria2等多线程下载器&#xff1b;   3、 IDM下载器&#xff1a;点击下载&#xff0c;或自行搜索&#xff1b;   4、 Fas…

探索 Noisee AI 的奇妙世界与变现之旅

日赚800&#xff0c;利用淘宝/闲鱼进行AI音乐售卖实操 如何让AI生成自己喜欢的歌曲-AI音乐创作的正确方式 抖音主播/电商人员有福了&#xff0c;利用Suno创作产品宣传&#xff0c;让产品动起来-小米Su7 用sunoAI写粤语歌的方法&#xff0c;博主已经亲自实践可行 五音不全也…

[经验] 涠洲岛在广西吗 #职场发展#知识分享#媒体

涠洲岛在广西吗 广西涠洲岛&#xff0c;是中国南海上的一颗闪亮明珠&#xff0c;位于广西北部湾沿海&#xff0c;东经108.71度&#xff0c;北纬21.54度&#xff0c;距离北海市区30公里&#xff0c;是中国最大的海岛之一&#xff0c;风景秀丽&#xff0c;气候温和。岛上山青水秀…

!力扣3. 无重复字符的最长子串

给定一个字符串 s &#xff0c;请你找出其中不含有重复字符的 最长子串的长度。 示例 1: 输入: s "abcabcbb" 输出: 3 解释: 因为无重复字符的最长子串是"abc"&#xff0c;所以其长度为 3 示例 2: 输入: s "bbbbb" 输出: 1 …

PCE自动装机

服务端和客户端 pxe&#xff1a;c/s模式&#xff0c;允许客户端通过远程服务器(服务端)下载引导镜像&#xff0c;加载安装吻技安&#xff0c;实现自动化安装操作系统。 无人值守&#xff1a;安装选项不需要认为干预&#xff0c;可以自动化实现。 pxe优点&#xff1a; 1.规模…

Overall timing accuracy 和Edge placement accuracy 理解

在电子设计自动化(EDA)、集成电路(IC)制造和高速数字电路设计领域,"Overall Timing Accuracy" 和 "Edge Placement Accuracy" 是两个关键的性能指标,它们对于确保电路的功能正确性和性能至关重要。 当涉及到“Overall timing accuracy”(总体时序精度)…