結果

問題 No.3586 Divide and Be Conquered
コンテスト
ユーザー marc2825
提出日時 2026-05-29 19:14:04
言語 C++17
(gcc 15.2.0 + boost 1.90.0)
コンパイル:
g++-15 -O2 -lm -std=c++17 -Wuninitialized -DONLINE_JUDGE -o a.out _filename_
実行:
./a.out
結果
RE  
実行時間 -
コード長 1,730 bytes
記録
記録タグの例:
初AC ショートコード 純ショートコード 純主流ショートコード 最速実行時間
コンパイル時間 1,255 ms
コンパイル使用メモリ 221,040 KB
実行使用メモリ 5,888 KB
最終ジャッジ日時 2026-07-10 20:56:23
合計ジャッジ時間 2,332 ms
ジャッジサーバーID
(参考情報)
judge2_0 / judge3_0
このコードへのチャレンジ
(要ログイン)
ファイルパターン 結果
sample AC * 1
other AC * 5 RE * 14
権限があれば一括ダウンロードができます

ソースコード

diff #
raw source code

#include <bits/stdc++.h>
using namespace std;

map<long long, int> memo;

// 山 x の値を愚直に計算する。
// 遷移の考え方:
// 山 x を選ぶ。
// 相手が x = a + b に分ける。
// 手番側は v(a), v(b) のうち好きな方を残せる。
//
// 「値 t にできる」とは、相手がどんな分割をしても、
// v(a) == t または v(b) == t が成り立つこと。
int grundy_bruteforce(long long x) {
    if (x <= 1) return 0;
    if (memo.count(x)) return memo[x];

    set<int> reachable;

    // t が「相手の任意分割に対して必ず残せる値」かを判定する
    for (int t = 0; t <= 100; ++t) {
        bool ok = true;

        for (long long a = 1; a <= x - 1; ++a) {
            long long b = x - a;

            int ga = grundy_bruteforce(a);
            int gb = grundy_bruteforce(b);

            if (ga != t && gb != t) {
                ok = false;
                break;
            }
        }

        if (ok) reachable.insert(t);
    }

    int g = 0;
    while (reachable.count(g)) g++;

    memo[x] = g;
    return g;
}

int main() {
    ios::sync_with_stdio(false);
    cin.tie(nullptr);

    int T;
    cin >> T;

    while (T--) {
        int N;
        cin >> N;

        int xr = 0;
        for (int i = 0; i < N; ++i) {
            long long A;
            cin >> A;

            // 愚直なので小さい値専用
            // 必要に応じて上限を調整してください
            if (A > 200) {
                cerr << "A is too large for brute force: " << A << '\n';
                return 1;
            }

            xr ^= grundy_bruteforce(A);
        }

        cout << (xr ? "First" : "Second") << '\n';
    }

    return 0;
}
0