HDU ACM 1024(最大子序列和)

2維表table[i][j] 表示將序列a1,a2,a3,...中的包含aj在內的j 個數分成i段,能得到的最大值。

So, table[i][j] = table[i][j-1] + aj  , 表示aj 與aj-1 同屬同一段。

       若aj與aj-1不再同一段, 則 table[i][j] = max(table[i-1][k]) + aj , (i-1<=k<j)

    求table第i行只需要用第i-1行,所以用動態數組來節省空間。

#include<iostream>
using namespace std;
const int M = 1000000;
long tmp[2][M];
int a[M];
inline long max(long &a ,long &b)
{
    return a>b?a:b;
}
int main()
{
    int m,n,t;

    long max_,res;
    while(scanf("%d%d",&m,&n)!=EOF)
    {
        t = 1 ;
        for(int i = 0 ; i < n-m ;i ++)
        {
            cin >> a[i];
            tmp[0][i] = 0;
        }
        for(int i = n-m; i < n ; i ++)
        {
            cin >> a[i];
        }
        for(int i = 0 ; i < m ;i++)        // i=0 的時候表示的是分1塊的情況。
        {
            if(i == 0)
            {
                max_ = -32768l;
                tmp[t][0] = a[0];
            }
            else 
            {
                max_ = tmp[1-t][i-1];
                tmp[t][i] = tmp[1-t][i-1]+a[i];
            }
            for(int j = i + 1 ; j <= n-m+i ; j++)
            {

                max_ = max(max_ , tmp[1-t][j-1]);
                tmp[t][j] = max(max_ , tmp[t][j-1]) + a[j];

            }
            t = 1 - t;
        }
        t = 1 - t;
        res = -32768*m;
        for(int i = m-1 ; i < n ; i ++)
        {
            res =max(tmp[t][i],res);
        }
        cout << res << endl;
    }
    return 0;
}


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章