segmentfault的诸位大大解决BUG的问题也是极为迅速,在此感谢一下。

title: "ACM-LA3177"
date: 2015-03-18 15:07:42
categories:
- ACM

白皮书给的答案没有考虑到n == 1的情况,然后还写了两个n,醉了。。

也是我一开始并没有真正的理解题解,反复考虑关于n == 1的问题还有 want[n] == want[0]
这个技巧。

对于循环的东西而言,可以将第一个补到最后作为 want[n] = want[0]

AC code

c#include <cstdio>
#include <algorithm>

using namespace std;

#define REP(i, n) for(int i = 0; i < (n); i++)

const int maxn = 100000 + 10;
int want[maxn], left[maxn], right[maxn];

int n;

bool test(int m)
{
    int x, y;
    left[0] = want[0], right[0] = 0;
    x = want[0], y = m - want[0];
    for(int i = 1; i < n; i++)
    {
        if(i % 2 == 0)
        {
            right[i] = min(y-right[i-1], want[i]);
            left[i] = want[i] - right[i];
        }
        else
        {
            left[i] = min(x-left[i-1], want[i]);
            right[i] = want[i] - left[i];
        }
    }
    return left[n-1] == 0;
}

int main()
{
    // freopen("input", "r", stdin);
    int L, R;
    while(scanf("%d", &n) == 1 && n)
    {
        for(int i = 0; i < n; i++) scanf("%d", &want[i]);
        want[n] = want[0];

        L = R = 0;
        for(int i = 0 ;i < n;i ++) L = max(L, want[i] + want[i+1]);

        if(n % 2)
        {
            for(int i = 0; i < n; i++) R = max(R, want[i]*3);
            while(L < R)
            {
                int M = (L+R)/2;
                if(test(M)) R = M; else L = M +1;
            }
        }
        if(n == 1) L = want[0];
        printf("%d\n", L);

    }
    return 0;
}

svtter
209 声望37 粉丝

更喜欢原型开发