整数二分从入门到精通

news2025/1/14 18:37:06

前言:

开个玩笑,我们写算法可不能这样哈~

好了,正片开始:

        你是否曾经也有过整数二分因为一直死循环而苦恼,你是否因为搞不清楚整数二分的边界处理而焦躁,明明很简单的一道二分,但是最后就是搞不出来答案来,本文,意在帮助我们在使用二分的时候能够正确的使用边界条件,避免死循环的产生,话不多说,我们开始发车

目录

1.二分问题的一般思路

首先,你的二分为什么会死循环?

mid到底加1还是不加1?

二分问题的模板

2.即学既练

3.金句省身


1.二分问题的一般思路

     如果你提前了解过二分的话,应该会知道二分最重要的就是中间值mid和自定义check函数,一般的我们会有如下的模板

while (l < r)
{
	int mid = (l + r) >> 1;
	if(check(mid))
		...
	else
		...
}

但是,这样固定化的模板可能会让我们在解决实际问题时错误的利用了边界条件导致while循环出现问题而出错,下面我们给出一些反面案例来验证上述模板的不严谨性:

首先,你的二分为什么会死循环?

mid到底加1还是不加1?

我们先来看二分的原理:

       

        我们来看第一种情况,如果我们的序列好巧不巧就只有两个,那我我们就有    l=r-1,那么我们的mid第一次求出来是l,如果恰好满足我们的true的情况,那么就会造成l和r的值永远不会更新,也就会导致死循环的产生,所以,对于第一种情况,我们应该让mid加上一个1,具体实现就是mid=(l+r+1)/2;

 所以我们这里大胆的总结出一套二分的模板来帮助大家理解记忆:

二分问题的模板

       我们需要根据题目条件判断我们所求的边界点属于满足条件的部分还是不满足条件的部分,也就是要根据所求边界点的不同来判断使用哪种模板来进行二分。

//当我们的区间[l,r]被划分为[l,mid-1]和[mid,r]时使用
int bserch1(int l, int r)
{
	while (l < r)
	{
		int mid = (l + r + 1) / 2;
		if (check(mid))
			l = mid;
		else
			r = mid - 1;
	}
}

//当区间被划分为[l,mid]和[mid+1,r]时使用
int  bserch2(int l, int r)
{
	while (l < r)
	{
		int mid = (l + r) >> 1;
		if (check(mid))
			r = mid;
		else
			l = mid + 1;
	}
}

2.即学既练

刚学了模板得拿出来练练手啊,别急,给你们准备了题目了,来人呐,上题~~~

 

 典型的二分法,我们首先来分析思路:

1.如何寻找起始点

这里我们要找到一个性质,也就是我们的check函数来帮助我们找到起始点,我们需要把起始点看左边界,那我们可以将a[mid]>=k设为条件,所有大于等于k的元素都会归入右半部分;

2.终止点

终止点的选择和上面的选择同理,我们需要另建一个二分,这次我们需要找到适合判断终止点的check函数来实现,什么样的条件可以让我们判断出终止点的位置呢?其实a[mid]<=k就可以,至于为什么,我画个图就好理解了。

 这样就比较好理解了,我们在选择条件时,尽量将满足条件的那一个部分作为一个整体加入一个满足或者不满足的部分,不要将这部分结果分开。

下面我们开始组织代码:

#include <bits/stdc++.h>

using namespace std;

const int maxn = 1e5 + 5;
int n,q;
int a[maxn];
int main()
{
	scanf("%d%d", &n, &q);
	for (int i = 0; i < n; i++)
		scanf("%d", &a[i]);
	while (q--)
	{

		int x;
		scanf("%d", &x);
		int l1 = 0, r1 = n - 1;
		//求起始点
		while (l1 < r1)
		{
			int mid = (l1 + r1) >> 1;//>>1相当于除2,同理,<<1相当于乘2
			if (a[mid] >= x)
				r1 = mid;//如果满足条件,那么mid一定在右半区域,也就是在起始点的右边或者是起始点上,所以我们最终返回的也是r1
			else
				l1 = mid + 1;
		}

		//求终止点
		int l2 = 0, r2 = n - 1;
		while (l2 < r2)
		{
			int mid = (l2 + r2+1) >> 1;
			if (a[mid] <= x)
				l2 = mid;//l2=mid,套模板我们有mid处需要加1,且最终返回l2
			else
				r2 = mid - 1;
		}

	    //我们有可能找不到结果,所以这里要判断
		if (a[r1]==x && a[l2]==x)
			printf("%d %d\n", r1, l2);
		else
			printf("-1 -1\n");
	}
	return 0;
}

总之,比较核心的就是二分模板的代码,我们可以这样记忆:当有条件l=mid出现时mid计算就要加1。

3.金句省身

你凭什么不努力?

     你所羡慕的高学历,经济独立,强大的能力都是别人用尽全力辛苦换来的,当你知道别人付出多少的时候,你可能也就不羡慕别人的生活了,你会发现此刻的你根本不配拥有。醒醒吧,每天幻想无济于事,真正阻碍你变好的是你自己。别再自我纵容,别再顾影自怜,是时候主动努力了。

     改变自己就是从逼自己一把开始的。哪有多少天赋异禀,不过是拼尽全力而已。

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

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

相关文章

Python入门教程+项目实战-9.1节: 字符串的定义与编码

目录 9.1.1 理解字符串 9.1.2 字符串的类型名 9.1.3 字符的数字编码 9.1.4 常用的字符编码 9.1.5 字符串的默认编码 9.1.6 字符串的编码与解码 9.1.7 转义字符详解 9.1.8 对字符串进行遍历 9.1.9 知识要点 9.1.10 系统学习python 9.1.1 理解字符串 理解字符串&#…

005:Mapbox GL添加全屏显示功能

第005个 点击查看专栏目录 本示例的目的是介绍演示如何在vue+mapbox中添加全屏显示功能 。 直接复制下面的 vue+mapbox源代码,操作2分钟即可运行实现效果 文章目录 示例效果配置方式示例源代码(共60行)相关API参考:专栏目标示例效果 配置方式 1)查看基础设置:https://…

还在因为写项目函数太多而烦恼?C++模板一文带你解决难题

&#x1f4d6;作者介绍&#xff1a;22级树莓人&#xff08;计算机专业&#xff09;&#xff0c;热爱编程&#xff1c;目前在c&#xff0b;&#xff0b;阶段>——目标Windows&#xff0c;MySQL&#xff0c;Qt&#xff0c;数据结构与算法&#xff0c;Linux&#xff0c;多线程&…

轮廓查找与绘制

轮廓查找与绘制 1)什么是轮廓 轮廓可以简单认为成将连续的点&#xff08;连着边界&#xff09;连在一起的曲线&#xff0c;具有相同的颜色或者灰度&#xff0c;提取轮廓就是提取 这些具有相同颜色或者灰度的曲线&#xff0c;或者说是连通域&#xff0c;轮廓在形状分析和物体…

学习系统编程No.20【进程间通信之命名管道】

引言&#xff1a; 北京时间&#xff1a;2023/4/15/10:34&#xff0c;今天起床时间9:25&#xff0c;睡了快8小时&#xff0c;昨天刷视屏刷了一个小时&#xff0c;本来12点的时候发完博客洗把脸就要睡了&#xff0c;可惜&#xff0c;看到了一个标题&#xff0c;说实话&#xff0…

.Net路由操作!!!!

什么是路由 问题 答案 路由是什么&#xff1f; 路由系统负责处理传入的请求并选择控制器和操作方法来处理它们。 路由系统还用于在视图中生成路由&#xff0c;称为传出的URL 路由有什么用&#xff1f; 路由系统能够灵活地处理请求&#xff0c;面不是将URL与Visual Studio…

MySQL(31)-ubuntu20.04-下安装mysql5.7

ubuntu20.04 下apt 默认安装的是8.0版本&#xff0c;如果要安装5.7版有如下3种方式&#xff1a; 1 下载 MySQL 二进制压缩包&#xff0c;解压并设置相关的参数即可运行 2 通过命令 apt install 进行安装&#xff0c;先下载 MySQL 5.7 对应的源&#xff0c;然后执行安装命令 ap…

5 分钟带你小程序入门 [实战总结分享]

微信小程序常常用 4 种文件类型 JS 文件 JS 在小程序中用于编写页面逻辑和交互效果&#xff0c;可调用 API 接口完成数据请求和处理&#xff0c;也可以使用第三方库和框架。 模块化编程&#xff1a;小程序中JS文件可以使用ES6的模块化语法&#xff0c;通过export和import来…

【vue3】关于watch与computed的用法看这个就ok

&#x1f609;博主&#xff1a;初映CY的前说(前端领域) ,&#x1f4d2;本文核心&#xff1a;watch()与computed的使用【vue2中watch|computed概念详解】&#xff0c;本文将介绍在vue3中怎么使用这两者技能 【前言】vue2当中有这两个技能&#xff0c;那么vue3中的watch与compute…

【云原生进阶之容器】第六章容器网络6.4.1--Flannel组网方案综述

《云原生进阶之容器》专题索引: 第一章Docker核心技术1.1节——Docker综述

【Unity】用HDRI作为Unity的Skybox

教程&#xff1a;用HDRI作为Unity的Skybox 在Unity中&#xff0c;Skybox是用于创建环境背景的一种组件。使用高动态范围图像&#xff08;HDRI&#xff09;作为Skybox可以提供更真实的环境背景。以下是使用HDRI作为Unity Skybox的步骤&#xff1a; 步骤1&#xff1a;下载HDRI图…

进销存管理系统能为企业带来哪些实际效益?

随着互联网的不断发展&#xff0c;如今的商业世界已经越来越向数字化转型。拥有一套完整的数字化的进销存管理能够极大地提升公司货物进出库存情况的效率和准确性&#xff0c;避免过程中出现不必要的错误和漏洞&#xff0c;从而帮助企业更加稳健地自我发展。那么&#xff0c;一…

华为MatePad有什么好用的软件?

现如今伴随着办公方式的转变&#xff0c;人们正迫切地寻找能够顺应时代的“生产力新工具”&#xff0c;它既要能够满足线上/线下灵活切换&#xff0c;又要具备绘画、键入、远程沟通、跨终端联动等多种功能。 对大多数人来说&#xff0c;日常使用华为平板只是满足一下娱乐和生活…

【SSA-LSTM】基于麻雀算法优化LSTM 模型预测研究(Matlab代码实现)

&#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;欢迎来到本博客❤️❤️&#x1f4a5;&#x1f4a5; &#x1f3c6;博主优势&#xff1a;&#x1f31e;&#x1f31e;&#x1f31e;博客内容尽量做到思维缜密&#xff0c;逻辑清晰&#xff0c;为了方便读者。 ⛳️座右铭&a…

超详细从入门到精通,pytest自动化测试框架实战-fixture固件高级操作(十一)

目录&#xff1a;导读前言一、Python编程入门到精通二、接口自动化项目实战三、Web自动化项目实战四、App自动化项目实战五、一线大厂简历六、测试开发DevOps体系七、常用自动化测试工具八、JMeter性能测试九、总结&#xff08;尾部小惊喜&#xff09;前言 参数化fixture fix…

深度学习随笔

一、SPP的作用 解决了训练CNN需要输入图像尺寸一致的问题。 一个CNN可看作由卷积、池化、全连接层组成&#xff0c;由于全连接层的权重矩阵是一个固定值&#xff0c;因此输入全连接层的特征图的维度也必须固定。 SPP利用多尺度思想解决了上述问题&#xff0c;使得神经网络的训练…

2023/4/16总结

深刻的了解了网络编程的一些知识点 socket:套接字 ServerSocket 用来声明服务器 Socket用来声明客户端&#xff0c;其实也不然&#xff0c;在serversocket的accept的方法中&#xff0c;返回的是一个socket变量。我觉得更像一个接口&#xff0c;网络接口。 InternetAddress可以…

PaddlePaddle NLP学习笔记1 词向量

文章目录1.语言模型 Language Model1.1 语言模型是什么1.2 语言模型计算什么1.3 n-gram Language Model2.神经网络语言模型NNLM2.1 N-gram模型的问题3. 词向量3.1 词向量(word Embedding)word2vec 词向量训练算法3.2 如何把词转换为词向量&#xff1f;3.3如何让向量具有语义信息…

Windows 下部署Redis 主从模式+哨兵模式+JAVA连接方式

前言 之前项目需求部署redis高可用&#xff0c;走了很多弯路以及相关配置来回折腾浪费了很多时间&#xff0c;特地记录下。 主从模式&#xff1a;实现多台redis实例进行服务运行&#xff0c;并且数据相互同步&#xff1b; 哨兵模式&#xff1a;实现主服务器和从服务器进行监听…

工业电子中的安森美深力科AMIS30660CANH2RG CAN收发器 面向工业自动化和汽车电源应用

工业电子中的安森美深力科AMIS30660CANH2RG CAN收发器 面向工业自动化和汽车电源应用 AMIS30660CANH2RG CAN 收发器是控制器区域网络 (CAN) 协议控制器和物理总线之间的接口&#xff0c;可在 12 V 和 24 V 系统中使用。该收发器为总线提供差分发射功能&#xff0c;向 CAN 控制…