UVA10684 The jackpot【前綴和+最值】

As Manuel wants to get rich fast and without too much work, he decided to make a career in gambling. Initially, he plans to study the gains and losses of players, so that, he can identify patterns of consecutive wins and elaborate a win-win strategy. But Manuel, as smart as he thinks he is, does not know how to program computers. So he hired you to write programs that will assist him in elaborating his strategy.
    Your first task is to write a program that identifies the maximum possible gain out of a sequence of bets. A bet is an amount of money and is either winning (and this is recorded as a positive value), or losing (and this is recorded as a negative value).
Input
The input set consists of a positive number N ≤ 10000 , that gives the length of the sequence, followed by N integers. Each bet is an integer greater than 0 and less than 1000.
    The input is terminated with N = 0.
Output
For each given input set, the output will echo a line with the corresponding solution. If the sequence shows no possibility to win money, then the output is the message ‘Losing streak.’
Sample Input
5
12 -4
-10 4
9
3
-2 -1 -2
0
Sample Output
The maximum winning streak is 13.
Losing streak.

問題鏈接UVA10684 The jackpot
問題簡述:輸入一個正整數n,再輸入n個整數,求最大子序列和。
問題分析
    這個問題看似一個動態規劃問題,可以用動態規劃來解決,確實是可以的,但是代碼比較繁瑣。還有一種解法是採用分治法來實現,可以參考歸併排序的思想來實現,但是代碼也比較繁瑣。
    也有更簡單的解法,就是使用前綴和的概念來解,可以不使用數組來存儲,維護前綴和的最小值和結果即可。
程序說明:給2個程序,使得問題更容易理解。
參考鏈接:(略)
題記:(略)

AC的C++語言程序如下:

/* UVA10684 The jackpot */

#include <bits/stdc++.h>

using namespace std;

int main()
{
    int n;
    while(~scanf("%d", &n) && n) {
        int a, sum = 0, lmin = 0, ans = INT_MIN;
        for(int i = 1; i <= n; i++) {
            scanf("%d", &a);
            sum += a;
            ans = max(ans, sum - lmin);
            lmin = min(lmin, sum);
        }

        if (ans > 0)  printf("The maximum winning streak is %d.\n", ans);
        else  printf("Losing streak.\n");
    }

    return 0;
}

AC的C++語言程序如下:

/* UVA10684 The jackpot */

#include <bits/stdc++.h>

using namespace std;

const int N = 10000;
int psum[N + 1];

int main()
{
    int n, a;
    while(~scanf("%d", &n) && n) {
        psum[0] = 0;
        for(int i = 1; i <= n; i++)
        {
            scanf("%d", &a);
            psum[i] = psum[i - 1] + a;
        }

        int ans = INT_MIN;
        for(int i = 1; i <= n; i++)
            for(int j = i + 1; j <=n; j++)
                ans = max(ans, psum[j] - psum[i]);

        if (ans > 0)  printf("The maximum winning streak is %d.\n", ans);
        else  printf("Losing streak.\n");
    }

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