题目1
题意:
给定长度为n的序列,可以将某个子序列乘以x,输出最大子区间和。
1
≤
n
≤
3
⋅
1
0
5
,
−
100
≤
x
≤
100
,
−
1
0
9
≤
a
i
≤
1
0
9
1≤n≤3⋅10^5,−100≤x≤100,−10^9≤a_i≤10^9
1≤n≤3⋅105,−100≤x≤100,−109≤ai≤109
分析:
对于答案的末尾,有三种可能:之前没有修改过,正在被修改,已经修改完了。就这样三种状态,所以自然就是dp转移了。能想到dp这题自然就解决了。
#include <iostream>
using namespace std;
typedef long long ll;
ll dp[300005][3];
ll a[300005];
int main()
{
ios::sync_with_stdio(false);
cin.tie(0);
int n,x;
cin >> n >> x;
for (int i = 1; i <= n; i++)
{
cin >> a[i];
}
ll ans = 0;
for (int i = 1; i <= n; i++)
{
dp[i][0] = max(dp[i][0],dp[i-1][0] + a[i]);
dp[i][1] = max(max(dp[i-1][1] + a[i] * x,dp[i-1][0] + a[i] * x),dp[i][1]);
dp[i][2] = max(max(dp[i-1][1]+a[i],dp[i-1][2]+a[i]),dp[i][2]);
ans = max(max(ans,dp[i][0]),max(dp[i][1],dp[i][2]));
}
cout << ans << '\n';
return 0;
}