HDU 1231 最大连续子序列:水dp

题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1231

题意:

  给你一个整数序列,求连续子序列元素之和最大,并输出该序列的首尾元素(若不唯一,输出首坐标最小的;首坐标相同输出尾坐标最小的)。

 

题解:

  O(N)做法。

  定义sum为当前坐标i之前某一段元素[x,i-1]之和。

  三种情况:

    (1)sum > 0:说明之前的和对答案有贡献,更新sum += a[i],tail = a。

    (2)sum < 0:前面的答案是拖后腿的。。。还不如从a[i]重新开始算,sum = a[i],head = a,tail = a。

    (3)sum = 0:可要可不要。但答案要求首坐标最小,就要了,同sum > 0的情况。

  如果某次sum > ans,则更新:ans = sum, lef = head,  rig = tail

 

AC Code:

 1 #include <iostream>
 2 #include <stdio.h>
 3 #include <string.h>
 4 #define INF 10000000
 5 
 6 using namespace std;
 7 
 8 int n;
 9 int a;
10 int ans;
11 int lef,rig;
12 int start,over;
13 
14 int main()
15 {
16     while(cin>>n)
17     {
18         if(n==0) break;
19         int head;
20         int tail=-1;
21         int sum=-INF;
22         ans=-INF;
23         for(int i=0;i<n;i++)
24         {
25             cin>>a;
26             if(i==0) start=a;
27             if(i==n-1) over=a;
28             if(sum>=0)
29             {
30                 sum+=a;
31                 tail=a;
32             }
33             else
34             {
35                 sum=a;
36                 head=a;
37                 tail=a;
38             }
39             if(sum>ans)
40             {
41                 ans=sum;
42                 lef=head;
43                 rig=tail;
44             }
45         }
46         if(ans>=0) cout<<ans<<" "<<lef<<" "<<rig<<endl;
47         else cout<<"0 "<<start<<" "<<over<<endl;
48     }
49 }

 

 

posted @ 2017-08-17 00:06  Leohh  阅读(140)  评论(0编辑  收藏  举报