最大子段和
题目描述
给出一个长度为 n n n 的序列 a a a,选出其中连续且非空的一段使得这段和最大。
输入格式
第一行是一个整数,表示序列的长度 n n n。
第二行有 n n n 个整数,第 i i i 个整数表示序列的第 i i i 个数字 a i a_i ai。
输出格式
输出一行一个整数表示答案。
样例
样例输入
7
2 -4 3 -1 2 -4 3
样例输出
4
提示
样例 1 解释
选取 [ 3 , 5 ] [3, 5] [3,5] 子段 { 3 , − 1 , 2 } \{3, -1, 2\} {3,−1,2},其和为 4 4 4。
数据规模与约定
- 对于 40 % 40\% 40% 的数据,保证 n ≤ 2 × 1 0 3 n \leq 2 \times 10^3 n≤2×103。
- 对于 100 % 100\% 100% 的数据,保证 1 ≤ n ≤ 2 × 1 0 5 1 \leq n \leq 2 \times 10^5 1≤n≤2×105, − 1 0 4 ≤ a i ≤ 1 0 4 -10^4 \leq a_i \leq 10^4 −104≤ai≤104。
基本方法
当解决最大连续子序列和问题时,可以使用两种基本方法:暴力法和动态规划法。
纯暴力
暴力法是最直观的解决方法,它通过遍历所有可能的子序列,并计算它们的和,最后返回最大的和。具体步骤如下:
初始化一个变量
m
a
x
x
maxx
maxx为负无穷大,用于记录最大和。
使用两个嵌套循环遍历所有可能的子序列起点和终点。
在内层循环中,计算当前子序列的和,并将其与
m
a
x
x
maxx
maxx进行比较,更新
m
a
x
x
maxx
maxx。
最后返回
m
a
x
x
maxx
maxx作为结果。
例如,对于序列
[
−
2
,
1
,
−
3
,
4
,
−
1
,
2
,
1
,
−
5
,
4
]
[-2, 1, -3, 4, -1, 2, 1, -5, 4]
[−2,1,−3,4,−1,2,1,−5,4],暴力法将遍历所有可能的子序列,计算它们的和,并返回最大的和,即
6
6
6,对应子序列
[
4
,
−
1
,
2
,
1
]
[4, -1, 2, 1]
[4,−1,2,1]。
暴力法的时间复杂度为 O ( n 2 ) O(n^2) O(n2),其中 n n n是序列的长度。
动态规划法
动态规划法是一种更高效的解决方法,它通过利用子问题的最优解来构建整个问题的最优解。具体步骤如下:
初始化两个变量
m
a
x
x
maxx
maxx和
l
l
ll
ll,分别用于记录全局最大和和当前子序列的和。
遍历整个序列,对于每个元素,将其与
l
l
ll
ll相加,如果结果大于当前元素本身,则更新
l
l
ll
ll为相加结果;否则,将
l
l
ll
ll更新为当前元素。
在每次更新
l
l
ll
ll时,将其与
m
a
x
x
maxx
maxx进行比较,如果
l
l
ll
ll大于
m
a
x
x
maxx
maxx,则更新
m
a
x
x
maxx
maxx为
l
l
ll
ll。
最后返回
m
a
x
x
maxx
maxx作为结果。
例如,对于序列
[
−
2
,
1
,
−
3
,
4
,
−
1
,
2
,
1
,
−
5
,
4
]
[-2, 1, -3, 4, -1, 2, 1, -5, 4]
[−2,1,−3,4,−1,2,1,−5,4],动态规划法将遍历整个序列,计算当前子序列的和,并更新
m
a
x
x
maxx
maxx和
l
l
ll
ll。最终,返回
m
a
x
x
maxx
maxx的值为
6
6
6,对应子序列
[
4
,
−
1
,
2
,
1
]
[4, -1, 2, 1]
[4,−1,2,1]。
动态规划法的时间复杂度为 O ( n ) O(n) O(n),其中 n n n是序列的长度。文章来源:https://www.toymoban.com/news/detail-769881.html
总结: 暴力法是一种简单直观的解决方法,但在处理大规模序列时效率较低。动态规划法通过利用子问题的最优解,将问题分解为更小的子问题,从而提高了效率。在实际应用中,动态规划法是解决最大连续子序列和问题的常用方法。文章来源地址https://www.toymoban.com/news/detail-769881.html
A C 代码
#include <bits/stdc++.h>
using namespace std;
long long n,a,ll,maxx;
int main() {
cin >>n >>a;
ll=a; maxx=a;
for (int i=2;i<=n;i++)
{
cin >>a;
if (ll+a<0)
ll=0;
else
{
ll+=a;
maxx=max(maxx,ll);
}
}
cout <<maxx;
return 0;
}
到了这里,关于【动态规划基础】求最大连续子序列和——最大子段和的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!