码迷,mamicode.com
首页 > 其他好文 > 详细

@atcoder - AGC002E@ Candy Piles

时间:2020-03-10 22:13:11      阅读:57      评论:0      收藏:0      [点我收藏+]

标签:pac   clu   href   建立   存在   糖果   accept   list   algo   


@description@

给定 N 堆糖果,第 i 堆包含 ai 个糖果。

现在两人进行博弈。有两种操作选择:
(1)吃掉包含最多糖果的糖果堆。
(2)每堆吃掉一颗。

吃掉最后一颗糖的人判输,问谁必胜?

原题传送门。

@solution@

将 n 个数从大到小排好序,看成一个 n 列的直方图,第 i 列包含 a‘i 个格子。

举个例子:对于 5 5 3 2 1 1,可以建立直方图如下:
o o
o o
o o o
o o o o
o o o o o o

那么相当于有一个棋子从 (1, 1) 出发,玩家可以将棋子右/上移一步,走出边界的判输。

然后经过万能的打表找规律,我们可以发现如果 (x, y) 和 (x + 1, y + 1) 同时存在,则两者的 np 状态。
不过这个结论利用反证法倒是不难证就是了。。。

于是我们可以先移动到一个点 (x, y) 使得 (x + 1, y + 1) 不存在,注意到从 (x, y) 只能一路向上或右,两种情况都判一判即可。

@accepted code@

#include <cstdio>
#include <algorithm>
using namespace std;

const int MAXN = 100000;

bool cmp(int x, int y) {return x > y;}

int a[MAXN + 5], N;
int main() {
    scanf("%d", &N);
    for(int i=1;i<=N;i++)
        scanf("%d", &a[i]);
    sort(a + 1, a + N + 1, cmp);
    for(int i=1;i<=N;i++) {
        if( a[i + 1] < i + 1 ) {
            int p = (a[i] - i) % 2, q;
            for(int j=i;j<=N+1;j++)
                if( a[j] < i ) {
                    q = (j - i - 1) % 2;
                    break;
                }
            puts(p & 1 || q & 1 ? "First" : "Second");
            break;
        }
    }
}

@details@

这是什么神仙操作.jpg。

我怎么觉得 E 比 F 难。F 题我好歹会切,E 题完全没有办法。

@atcoder - AGC002E@ Candy Piles

标签:pac   clu   href   建立   存在   糖果   accept   list   algo   

原文地址:https://www.cnblogs.com/Tiw-Air-OAO/p/12458697.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!