「日常训练」More Cowbell(Codeforces Round #334 Div.2 B)

题意与分析(CodeForces 604B)

题意是这样的:(n)个数字,(k)个盒子,把(n)个数放入(k)个盒子中,每个盒子最多只能放两个数字,问盒子容量的最小值是多少(水题)
不要看到这种题目什么都不想,看见最大容量最小值就是起手一个二分,这题运用贪心的思想会更简单。
想一想紫书上有一题是类似的,两个人坐船过河的,也是同样的思路。
我们一定要注意到这样一个结论:如果第一个数没法和某一个数放在一起,那么大于等于它的数一定都只能一个单独的盒子了。设这个数是第(p)个,那么就是有(n-(p+1)+1=n-p)个数是一个盒子放着的,而有(frac p2)个数是合并着放在一起的。显然有(n-p+frac p2=k),代入化简有(2n-2p+p=2k),从而有(p=2n-2k),也就是前(2(n-k))个数必须手拉手放在一起才能够满足题意。但是呢,有可能k比n大,这么直接写就有可能出错。我们不妨从中间往两边扩散,测试掉前(k)对直到不合法为止,然后让它与最后一个最大的单个比较一下就行了。

代码

/* ACM Code written by Sam X or his teammates.
 * Filename: cfr334d2b.cpp
 * Date: 2018-11-05
 */

#include <bits/stdc++.h>

#define INF 0x3f3f3f3f
#define PB emplace_back
#define MP make_pair
#define fi first
#define se second
#define rep(i,a,b) for(repType i=(a); i<=(b); ++i)
#define per(i,a,b) for(repType i=(a); i>=(b); --i)
#define ZERO(x) memset(x, 0, sizeof(x))
#define MS(x,y) memset(x, y, sizeof(x))
#define ALL(x) (x).begin(), (x).end()

#define QUICKIO                  
    ios::sync_with_stdio(false); 
    cin.tie(0);                  
    cout.tie(0);
#define DEBUG(...) fprintf(stderr, __VA_ARGS__), fflush(stderr)

using namespace std;
using pi=pair<int,int>;
using repType=int;
using ll=long long;
using ld=long double;
using ull=unsigned long long;

int n,k,s[100005];

int
main()
{
    scanf("%d%d", &n, &k);
    rep(i,1,n)
    {
        scanf("%d", &s[i]);
    }
    int ans=0;
    int l=n-k,r=n-k+1;
    for(;l>=1&&r<=n;--l,++r)
        ans=max(ans,s[l]+s[r]);
    ans=max(ans,s[n]);
    cout<<ans<<endl;
    return 0;
}
如非注明,原创内容遵循GFDLv1.3发布;其中的代码遵循GPLv3发布。
原文地址:https://www.cnblogs.com/samhx/p/CFR334D2B.html