当前位置: 首页 > news >正文

蓝桥杯备考:二分答案之数列分段

看到最大值最小,我们第一个想到就是二分答案

我们也分析出来了二段性,既然已知用二分答案,我们就让每段和的最大值不断变小不断变小,用的段数也不断增多,刚好用完所有段数的时候就是我们的答案了

我们不断的check看符不符合要求,符合要求就不断接近答案,不符合要求就排除

check函数怎么写呢?

我们已经枚举出了最大值,我们只要让每段和最大不超过最大值,然后判断段数是大于m还是小于还是等于m就行了

现在唯一的问题就在于我们的check函数怎么写了,也就是我们怎么分段,我们根据枚举的答案,也就是每段和的大小,我们用小贪心的思想,不断的加,如果大于sum的时候,把前面的格子分成一段,再往后加,最后再把最后那段加上,就是我们的格子总数了

我们判断格子总数是小于m还是大于等于m,也就是我们把段数尽可能分的最少,总段数是有限的

来进行我们的二分操作,我们判断一下二分的两个端点,每段和的最大值最大就是sum(a[i),最小值就是max(a[i]) 

#include <iostream>
using namespace std;
typedef long long ll;
const int N = 1e5+10;
ll a[N];
ll n,m;
bool check(ll x)
{
	ll sum = 0;
	ll cnt = 0;
	for(int i =1;i<=n;i++)
	{
		sum+=a[i];
		if(sum>x)
		{
			cnt++;
			sum=a[i];
		 }
		
	}
	return cnt+1<=m;
}
int main()
{
	cin >> n >> m;
	ll l = 0,r = 0;
	for(int i = 1;i<=n;i++)
	{
		cin >> a[i];
		l = max(l,a[i]);	
		r+=a[i];
	}
	while(l<r)
	{
		ll mid = (l+r)/2;
		if(check(mid)) r=mid;
		else l = mid+1;
	}
	cout << l << endl;
	
	
	
	return 0;
 } 

相关文章:

  • python暴力破解html表单
  • 【网络】网关
  • 【C++】结构体中的 std::string:赋值操作的安全性与 memset和memcpy 的陷阱
  • 将Wi-Fi模块订阅MQTT主题以获取最新的固件版本推送信息
  • NAT 模式
  • Hive根据输入数据量计算reducer的数量,这个输入数据量是map阶段的输出结果还是客户端提交任务时的数据量?
  • MongoDB 面试备战指南
  • 0.http协议详解
  • 地理信息可视化技术大全【WebGIS 教程一】
  • 软考系统架构师论文模版及实例
  • Spring Boot 项目打包运行
  • 项目流程中关键节点的测试类型
  • Spring IOC容器详解:深入理解控制反转与依赖注入
  • MySQL |表的约束
  • Unity Shader编程】之复杂光照
  • Box-Cox变换:让数据服从正态分布的数学魔法
  • node-red s7.net
  • Java 基础面试题
  • 常考计算机操作系统面试习题(一下)
  • Matlab教程001:软件介绍和界面使用
  • 未来之城湖州,正在书写怎样的城市未来
  • 警方通报男子地铁上拍视频致乘客恐慌受伤:列车运行一度延误,已行拘
  • 中俄就应对美加征所谓“对等关税”等问题进行深入交流
  • 习近平会见缅甸领导人敏昂莱
  • 异域拾异|大脚怪的形状:一项神秘社会学研究
  • 晋级中部非省会第一城,宜昌凭什么