二分查找_在排序数组中查找元素的第一个和最后一个位置

1.朴素二分查找

.二分查找

二分查找思路:
1.left=0,right=nums.size()-1(最后一个元素下标),取中间元素下标 mid=left+(right-left)/2 (防溢出)

2.nums[mid]>target ,说明mid右边的元素都大于target,就不用再从mid右边查找。right=mid-1

3.nums[mid]<target ,说明mid左边的元素都小于target,就不用再从mid左边查找。

left=mid+1

4.nums[mid]==tartget,找到目标值返回。

5.循环条件 left<=right,当left==right时,意味着只剩最后一个元素,有可能是目标值。

不断循环直到找到目标结果,或者left>right不满足循环条件。

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

2.查找区间左端点/右端点

在排序数组中查找元素的第一个和最后一个位置

这道题如果用朴素二分查找,虽然可以找到target==8的元素,但不一定就是目标值。

找到目标值再向左 向又查找不行吗?可以,但效率会降低。我们有其它方法可以更好的解决。

1.查找区间左端点

该方法对于朴素二分法不同的是,朴素二分法把区间分为3份,>target ==target <target。

查找区间左端点把区间分为2份,<target >=target(默认非递减)。

eg1.[5 7 7]  [8 8 10] 而目标值就在右区间的最左边。

1.如果mid落在左区间,mid指向的元素肯定不是目标值,可以让left=mid+1

2.如果mid落在右区间,mid指向的元素有可能是目标值,所以让right=mid 如果-1可能会跳过目标值。

所以right只会在右区间移动,而left最远只会到右区间的最左边。所以当left==right就可以求出结果。

3.循环条件为left<right,不能是left<=right,如果等于会一直循环,left==right

mid=(left+right)/2 mid值不变,还是在右区间,right=mid right值也不变。

4.mid的取值,mid=left+(right-left) 还是向上取整 mid=left+(right-left+1)?有什么区别?

如果只剩两个数[5 7 7]  [8 8 10] 的7 8。left指向7 right指向8,mid=left+(right-left+1) mid=1

此时mid指向8,落在右区间,right=mid。再取mid还是指向8,就会无限循环。

所以mid=left+(right-left) mid=0取靠左边的值,指向7,落在左区间,left=mid+1。此时left==right循环结束。

下面举2种极端情况

1.数组值全>target 只有右区间,right不断移动 left==0不动.left==right指向下标0

2.数组值全<arget 只有左区间,left不断移动 right==nums.szie()-1不动.left==right指向最后一个元素(因为mid=left+(right-left) mid=0取靠左边的值 不会出现mid==right left=mid+1越界的情况

 2.查找区间右端点

和查找左端点本质一样,但细节不同。

查找区间右端点把区间分为2份,<=target >target(默认非递减)。

eg1.[5 7 7 8 8] [ 10 ] 而目标值就在左区间的最右边。

1.如果mid落在右区间,mid指向的元素肯定不是目标值,可以让right=mid-1 

2.如果mid落在左区间,mid指向的元素可能是目标值,所以让left=mid 

所以left只会在左区间移动,而right最远只会到左区间的最右边。所以当left==right就可以求出结果。

3.循环条件为left<right,不能是left<=right,如果等于会一直循环,left==right

mid=(left+right)/2 mid值不变,还是在左区间,left=mid left值也不变。

4.mid的取值,mid=left+(right-left) 还是向上取整 mid=left+(right-left+1)?有什么区别?

如果只剩两个数[5 7 7 8 8 ][10] 的8 10。left指向8 right指向10,mid=left+(right-left) mid=0取靠左边的值 此时mid指向8,落在左区间,left=mid。再取mid还是指向8,就会无限循环。

所以mid=left+(right-left+1) mid=1取靠右边的值,指向10,落在右区间,right=mid-1。此时left==right循环结束。

class Solution {
public:vector<int> searchRange(vector<int>& nums, int target) {int le=-1,ri=-1;int left=0,right=nums.size()-1,mid=0;//处理边界情况if(nums.empty()) return {-1,-1};//取左端点下标while(left<right){mid=left+(right-left)/2;//取靠左边的值if(nums[mid]<target)left=mid+1;elseright=mid;}le=left;left=0,right=nums.size()-1;//取右端点下标while(left<right){mid=left+(right-left+1)/2;//取靠右边的值if(nums[mid]<=target)left=mid;elseright=mid-1;}ri=left;if(nums[left]==target) return {le,ri};else return {-1,-1}; //没找到的情况}
};

1.如果目标值是左端点,就把它套在右区间[5 7 7]  [8 8 10],让左边的+1来找,mid就要取靠左的值

2.如果目标值是右端点,就把它套在左区间[5 7 7 8 8 ][10],让右边的-1来找,mid就要取靠右的值

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

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

相关文章

Discuz 论坛开发一套传奇发布站与传奇开服表

Discuz 论坛开发一套传奇发布站与传奇开服表 随着互联网技术的飞速发展&#xff0c;网络游戏已成为人们休闲娱乐的重要方式之一。在众多网络游戏中&#xff0c;传奇系列以其独特的魅力吸引了大量忠实玩家。为了满足这些玩家的需求&#xff0c;并促进游戏信息的交流与分享&…

QtCreator通过CMake多文件编译.cpp、.qss、.h、.ui文件,达到MVC三层架构的效果

博主在构建C项目的时候&#xff0c;一般都喜欢将头文件和源文件分开为不同的文件夹&#xff0c;比如include目录下只存放.h文件和.ui文件&#xff0c;src目录下只存放.cpp和.qss文件&#xff0c;res目录下只存放图片、音频等文件&#xff0c;这时候使用CMake对项目进行分文件管…

qml圆形图片,qml圆形头像制作

代码比较简单&#xff0c;就不细讲了&#xff0c;大家直接看下面源码吧&#xff01;如果对你有所帮助&#xff0c;可以帮角角点个关注嘛&#xff1f; import QtQuick import QtQuick.Effects import Qt5Compat.GraphicalEffectsWindow {width: 640height: 480visible: truetit…

使用代理服务器后sse数据合并问题

如果是使用本地代理服务器devServer compress:false,如果是发布到生产环境下的代理服务器nginx 增加如下配置&#xff0c;该配置同时支持websocket和sse proxy_http_version 1.1; #设置代理请求使用 HTTP/1.1 版本。WebSocket 需要 HTTP/1.1&#xff0c;因为它支持持久连接和更…

【每日一题】LeetCode - 盛最多水的容器

给定一个长度为 n 的整数数组 height。有 n 条垂线&#xff0c;第 i 条线的两个端点是 (i, 0) 和 (i, height[i])。要求找出其中的两条线&#xff0c;使得它们与 x 轴共同构成的容器可以容纳最多的水。 输入示例&#xff1a; height [1,8,6,2,5,4,8,3,7]输出&#xff1a; 4…

Python快速入门教程

目录 1. Python 简介 2. 环境准备 3. 第一个 Python 程序 4. 变量与数据类型 5. 基本操作与控制结构 6. 函数与模块 7. 实践项目 结语 Python 是一种非常友好的编程语言&#xff0c;特别适合初学者。它的语法简洁&#xff0c;容易上手&#xff0c;并且广泛应用于各种领…

C++结合图形编程与物联网:你更偏向哪种方式来学习信息学奥赛?

随着信息学奥赛在全国范围内的热度逐年攀升&#xff0c;学生和家长们越来越重视如何有效备赛。传统的编程学习方式侧重于算法和数据结构&#xff0c;但随着科技的发展&#xff0c;图形化编程与物联网&#xff08;IoT&#xff09;项目逐渐成为新兴的学习路径。通过C结合图形化编…

Rust 力扣 - 1. 两数相加

文章目录 题目描述题解思路题解代码题目链接 题目描述 题解思路 我们使用一个全局的备忘录&#xff0c;然后我们遍历数组&#xff0c;如果当前元素在备忘录里面找到了&#xff0c;就返回备忘录里面记录的下标和当前下标记录&#xff0c;没找到就把当前元素匹配的元素和当前元素…

人工智能_神经网络103_感知机_感知机工作原理_感知机具备学习能力_在学习过程中自我调整权重_优化效果_多元线性回归_逻辑回归---人工智能工作笔记0228

由于之前一直对神经网络不是特别清楚,尤其是对神经网络中的一些具体的概念,包括循环,神经网络卷积神经网络以及他们具体的作用,都是应用于什么方向不是特别清楚,所以现在我们来做教程来具体明确一下。 当然在机器学习之后还有深度学习,然后在深度学习中对各种神经网络的…

Java对称加密:AES 高级加密标准

1、对称加密简述 对称加密&#xff0c;又称对称密钥加密或私钥加密&#xff0c;是一种在加密和解密过程中使用相同一个密钥的加密算法。这种加密方式的核心在于&#xff0c;发送方使用某个密钥对数据进行加密&#xff0c;接收方则使用完全相同的密钥对数据进行解密。由于加密和…

基于物联网的智慧考场系统设计(论文+源码)

1. 功能设计 &#xff08;1&#xff09;温度监测与控制功能&#xff1a; 系统需要能够实时采集考场内的温度信息&#xff0c;通过DS18B20传感器获取准确的数据&#xff0c;并在OLED屏幕和APP上显示。当温度异常过高时&#xff0c;系统应自动启动继电器&#xff0c;模拟空调开启…

数字IC后端实现 | Innovus各个阶段常用命令汇总

应各位读者要求&#xff0c;小编最近按照Innovus流程顺序整理出数字IC后端项目中常用的命令汇总。限于篇幅&#xff0c;这次只更新到powerplan阶段。有了这份Innovus常用命令汇总&#xff0c;学习数字IC后端从此不再迷路&#xff01;如果大家觉得这个专题还不错&#xff0c;想继…

C语言_动态内存管理

本章重点 为什么存在动态内存分配 动态内存函数的介绍 malloc free calloc realloc 常见的动态内存错误 几个经典的笔试题 柔性数组 1. 为什么存在动态内存分配 我们已经掌握的内存开辟方式有&#xff1a; int val 20;//在栈空间上开辟四个字节 char arr[10] {0}…

Maven进阶——坐标、依赖、仓库

目录 1.pomxml文件 2. 坐标 2.1 坐标的概念 2.2 坐标的意义 2.3 坐标的含义 2.4 自己项目的坐标 2.5 第三方项目坐标 3. 依赖 3.1 依赖的意义 3.2 依赖的使用 3.3 第三方依赖的查找方法 3.4 依赖范围 3.5 依赖传递和可选依赖 3.5.1 依赖传递 3.5.2 依赖范围对传…

算法的学习笔记—数组中的逆序对(牛客JZ51)

&#x1f600;前言 在算法和数据结构领域&#xff0c;"逆序对"是一个经典问题。它在数组中两个数字之间定义&#xff0c;若前面的数字大于后面的数字&#xff0c;则这两个数字组成一个逆序对。我们要做的就是&#xff0c;给定一个数组&#xff0c;找出数组中所有的逆…

Docker 镜像下载问题及解决办法

Docker 镜像下载问题及解决办法 我在杂乱的、破旧的村庄寂寞地走过漫长的雨季&#xff0c;将我年少的眼光从晦暗的日子里打捞出来的是一棵棵开花的树&#xff0c;它们以一串串卓然不俗的花擦明了我的眼睛&#xff0c;也洗净了我的灵魂。 引言 在使用 Docker 时&#xff0c;用户…

【AI绘画】Midjourney进阶:对角线构图详解

博客主页&#xff1a; [小ᶻZ࿆] 本文专栏: AI绘画 | Midjourney 文章目录 &#x1f4af;前言&#x1f4af;什么是构图为什么Midjourney要使用构图 &#x1f4af;对角线构图特点应用场景提示词书写技巧测试 &#x1f4af;小结 &#x1f4af;前言 【AI绘画】Midjourney进阶&a…

免费送源码:Java+MVC+HTML+CSS +MySQL 考研资料共享系统的设计与实现 计算机毕业设计原创定制

摘 要 随着互联网趋势的到来&#xff0c;各行各业都在考虑利用互联网将自己推广出去&#xff0c;最好方式就是建立自己的互联网系统&#xff0c;并对其进行维护和管理。在现实运用中&#xff0c;应用软件的工作规则和开发步骤&#xff0c;采用Java技术建设考研资料共享系统。 本…

Win10+MinGW13.1.0编译Qt5.15.15

安装windows SDK、python、ruby、cmake、Perl[可选]安装MySQL解压qt-everywhere-opensource-src-5.15.15.zip&#xff08;注&#xff1a;不要使用qt-everywhere-opensource-src-5.15.15.tar.xz&#xff09;修改源代码 E:\qt-everywhere-src-5.15.15\qtbase\src\3rdparty\angle\…

028_Comma_Separated_List_in_Matlab中的逗号分割列表

什么是逗号分割列表 这玩意一般都不知道是什么&#xff0c;Comma-separated list&#xff0c;CSL&#xff0c; 虽然&#xff0c;用Matlab的时候天天会用到。这到底是个什么玩意&#xff1f;或者&#xff0c;更进一步&#xff0c;这到底是不是个玩意&#xff1f; 每次调用一个…