[Daimayuan] 分段求和(C++,二分)

news/2024/10/20 18:55:15/

对于给定的一个长度为 N N N 的正整数数列 A 1 − N A_{1−N} A1N,现要将其分成 M ( M ≤ N ) M(M≤N) M(MN) 段,并要求每段连续,且每段和的最大值最小。

关于最大值最小:

例如一数列 4 , 2 , 4 , 5 , 1 4,2,4,5,1 4,2,4,5,1 要分成 3 3 3 段。

将其如下分段: [ 4 , 2 ] [ 4 , 5 ] [ 1 ] [4,2][4,5][1] [4,2][4,5][1]。 第一段和为 6 6 6,第 2 2 2 段和为 9 9 9,第 3 3 3 段和为 1 1 1,和最大值为 9 9 9

将其如下分段: [ 4 ] [ 2 , 4 ] [ 5 , 1 ] [4][2,4][5,1] [4][2,4][5,1]。第一段和为 4 4 4,第 2 2 2 段和为 6 6 6,第 3 3 3 段和为 6 6 6,和最大值为 6 6 6

并且无论如何分段,最大值不会小于 6 6 6

所以可以得到要将数列 4 , 2 , 4 , 5 , 1 4,2,4,5,1 4,2,4,5,1 要分成 3 3 3 段,每段和的最大值最小为 6 6 6

输入格式

1 1 1 行包含两个正整数 N , M N,M N,M

2 2 2 行包含 N N N 个空格隔开的非负整数 A i A_i Ai,含义如题目所述。

数据范围

1 ≤ N ≤ 1 0 5 , M ≤ N , A i ≤ 1 0 8 1≤N≤10^5,M≤N,A_i≤10^8 1N105,MN,Ai108

输出格式

一个正整数,即每段和最大值最小为多少。

输入样例

5 3
4 2 4 5 1

输出样例

6

解题思路

没有一套标准的算法用于此题,只能进行搜索。

暴力搜索直接 T T T飞,考虑到题中要求是最小的最大值,所以采用二分搜索法。

二分答案:限制分段和的最大值越小,分段越多;反之,分段越少。

判断函数如下:

bool judge(long long x) {int l = 0, cnt = 0;for (int r = 1; r <= n; r++) {if (arr[r] - arr[l] > x) {l = r - 1;cnt++;}}return ++cnt <= m;//分段数越多,越容易符合题中要求的分段数
}

不断拓展区间,区间和小于上限则继续,大于上限则累计分段数,然后进行下个区间的计算。

二分主体如下:

long long bin_search() {long long l = max_num - 1, r = arr[n] + 1, mid;while (l + 1 != r) {mid = l + r >> 1;if (judge(mid)) r = mid;else l = mid;}return r;//符合题意的最小限制值
}

通过l = nax_num - 1来限制每段中至少含有一个元素, [ 0 , l ] [0,l] [0,l]是不符合题意的限制值, [ r , a r r [ n ] ] [r,arr[n]] [r,arr[n]]是符合题意的限制值。

最后,AC代码如下:

#include <iostream>
using namespace std;
const int max_n = 1e5;
const int max_a = 1e8;
const int max_m = max_n;long long arr[max_n + 1], max_num = 0;
int n, m;bool judge(long long x) {int l = 0, cnt = 0;for (int r = 1; r <= n; r++) {if (arr[r] - arr[l] > x) {l = r - 1;cnt++;}}return ++cnt <= m;
}long long bin_search() {long long l = max_num - 1, r = arr[n] + 1, mid;while (l + 1 != r) {mid = l + r >> 1;if (judge(mid)) r = mid;else l = mid;}return r;
}int main() {cin >> n >> m;for (int i = 1; i <= n; i++) {cin >> arr[i];max_num = max(max_num, arr[i]);arr[i] += arr[i - 1];//数组前缀和}cout << bin_search() << endl;return 0;
}

http://www.ppmy.cn/news/342675.html

相关文章

谷歌Imagen Editor融入AI技术,助力图片创作

AI科技的应用越来越广泛&#xff0c;自然也被各个公司所重视&#xff0c;近日谷歌就推出利用AI技术的图片创作软件Imagen Editor&#xff0c;这款软件成熟以后&#xff0c;或将助力图片的创作。 近日有消息称&#xff0c;谷歌正在研发一款名为Imagen Editor生成式AI工具&…

java:找不到符号 符号:变量:log get set

问题&#xff1a;java&#xff1a;找不到符号&#xff1a;变量&#xff1a;log get set解决方法&#xff1a;在idea中&#xff0c;点击file-Settings&#xff0c;打开配置页面&#xff0c;如图红框位置&#xff0c;输入&#xff1a; -Djps.track.ap.dependenciesfalse

亚马逊美国站 儿童珠宝首饰CPC认证 ASTM F2923标准CPSIA检测报告

为什么越来越多人爱送珠宝给宝宝? 1、有人说每个小孩子都是来自神的恩典&#xff0c;他们就像父母最珍贵的珠宝值得用一生的时间去呵护与珍藏。 2、西班牙人认为&#xff0c;儿童珠宝作为他们的第一份礼物&#xff0c;会庇佑孩子们未来过上非常幸福&#xff0c;繁荣而成功的…

一分钟了解什么nft数字藏品,有什么价值

NFT&#xff08;Non-Fungible Token&#xff09;数字藏品是一种基于区块链技术的数字资产&#xff0c;具有唯一性和不可替代性。它们是数字文件的独特表示&#xff0c;通过区块链的不可篡改性和透明性确保其真实性和所有权。相比传统的数字文件&#xff0c;NFT数字藏品在艺术、…

react中如何给为一个元素规定多个类,以及给元素添加行内样式,内部样式和外部样式

react中如何给为一个元素规定多个类&#xff0c;以及给元素添加行内样式&#xff0c;内部样式和外部样式 为一个元素规定多个类(静态添加)为一个元素规定多个类(动态添加)行内样式内部样式外部样式 为一个元素规定多个类(静态添加) <div className{tipsTxt tipsStyle}>通…

uniapp支付页面模板

支付组件 <template><view><u-popup v-model"show" mode"bottom" :closeable"true" close"close"><view class"plr-40"><view class"center ptb-30">选择支付方式</view>&l…

上位机工业协议-FinsTCP

1、欧姆龙设备通信 - PLC&#xff1a;系列 CS系列、CJ系列、CP系列、NX系列 &#xff08;1&#xff09;微型&#xff1a;CPM1A、CPM2A、CP1H、CP1L&#xff08;2&#xff09;小型&#xff1a;CPM2C、CQM1H、CJ1M&#xff08;3&#xff09;中型&#xff1a;C200H、CJ1、CS1&…

易班学生安全上报系统脚本

转眼飞逝&#xff0c;还没回过神来暑假就过去了一半。时间过得真快。 今天&#xff0c;我又被班里同学&#xff0c;同学催着上报易班&#xff0c;淦&#xff01;仔细想想&#xff0c;我这一个暑假被催的次数好像挺多的。然后脑子一机灵&#xff0c;我干脆编个脚本来上报。本来想…