0
点赞
收藏
分享

微信扫一扫

【线性DP 子序列和】Max Sum(HDU-1003)


【线性DP 子序列和】Max Sum(HDU-1003)

题目

Problem Description
Given a sequence a[1],a[2],a[3]…a[n], your job is to calculate the max sum of a sub-sequence. For example, given (6,-1,5,4,-7), the max sum in this sequence is 6 + (-1) + 5 + 4 = 14.

Input
The first line of the input contains an integer T(1<=T<=20) which means the number of test cases. Then T lines follow, each line starts with a number N(1<=N<=100000), then N integers followed(all the integers are between -1000 and 1000).

Output
For each test case, you should output two lines. The first line is “Case #:”, # means the number of the test case. The second line contains three integers, the Max Sum in the sequence, the start position of the sub-sequence, the end position of the sub-sequence. If there are more than one result, output the first one. Output a blank line between two cases.

Sample Input

2
5 6 -1 5 4 -7
7 0 6 -1 1 -6 7 -5

Sample Output

Case 1:
14 1 4

Case 2:
7 1 6

思路

求最大连续子序列和还要找出首尾区间
主要是累加sum
如果sum>max_sum那么更新区间并累加
如果sum<0那么直接舍弃sum设为0,开始下一个
主要是找首尾区间啊啊写了好几发全都蜜汁WA了

代码

个人过不了的两个代码

#include<bits/stdc++.h>
using namespace std;
int T,n;
const int N=1e5+10,INF=0x3f3f3f3f;
typedef long long ll;
int a[N],f[N];
int main()
{
scanf("%d",&T);
for(int C=1;C<=T;C++)
{
scanf("%d",&n);
for(int i=1;i<=n;i++)scanf("%d",&a[i]);

int st=1,ed=1,ans=-INF;
int sum=0;
int tmpl=st;
for(int i=1;i<=N;i++)
{
sum+=a[i];
if(sum>ans)
{
ans=sum;
st=tmpl;
ed=i;
}
if(sum<0)
{
sum=0;
tmpl=i+1;
}
}
printf("Case %d:\n%d %d %d\n",C,ans,st,ed);
if(C<T)printf("\n");
}
return 0;
}

#include<bits/stdc++.h>
using namespace std;
int T,n;
const int N=1e5+10,INF=0x3f3f3f3f;
typedef long long ll;
int a[N],s[N],f[N];
int main()
{
scanf("%d",&T);
for(int C=1;C<=T;C++)
{
scanf("%d",&n);
memset(s,0,sizeof (s));
memset(s,0,sizeof (f));
for(int i=1;i<=n;i++)
{
scanf("%d",&a[i]);
s[i]=s[i-1]+a[i];
}
int st=1,ed=1,ans=-INF;
for(int j=1,i=1;j<=n&&i<=j;j++)
{
while(s[j]-s[i-1]<0&&i<j)i++;
if(s[j]-s[i-1]>ans)
{
// printf("gx %d~%d=~%d\n",i,j,s[j]-s[i-1]);
ans=s[j]-s[i-1];
st=i;ed=j;
}
}
printf("Case %d:\n%d %d %d\n",C,ans,st,ed);
if(C<T)printf("\n");
}
return 0;
}

看别的大佬的AC代码
分开找起点和终点

#include <stdio.h>
#include <string.h>
#include <math.h>
int main()
{
int t,n,k=1;
scanf("%d",&t);
while(k<=t)
{
scanf("%d",&n);
int a[100001],max=-1000,start=0,end=0,i,sum=0;
for(i=1;i<=n;i++)
{
scanf("%d",&a[i]);
sum+=a[i];
if(sum>max)
{
max=sum;
end=i;
}
if(sum<0)
sum=0;
}
sum=0;
for(i=end;i>0;i--)
{
sum+=a[i];
if(sum==max)
start=i;
}
printf("Case %d:\n",k);
printf("%d %d %d\n",max,start,end);
if(k!=t)
printf("\n");
k++;
}
return 0;
}


举报

相关推荐

0 条评论