Submission #36654838


Source Code Expand

// #define NDEBUG
#include <bits/stdc++.h>

#define REP_(i, a_, b_, a, b, ...) for (int i = (a), END_##i = (b); i < END_##i; ++i)
#define REP(i, ...) REP_(i, __VA_ARGS__, __VA_ARGS__, 0, __VA_ARGS__)
#define ALL(x) std::begin(x), std::end(x)
using Int = long long;
using Uint = unsigned long long;
using Real = long double;

template<typename T, typename U>
inline bool chmax(T &a, U b) { return a < b and ((a = b), true); }
template<typename T, typename U>
inline bool chmin(T &a, U b) { return a > b and ((a = b), true); }
template<typename T>
constexpr T kBig = std::numeric_limits<T>::max() / 2;
#if __cplusplus < 202002L
template<typename T>
inline int ssize(const T &a) { return (int) a.size(); }
#endif

[[noreturn]] void exit_() {
  fflush(stdout), fflush(stderr);
  std::cout.flush(), std::cerr.flush();
  std::_Exit(0);
}

void TLE() {
  double x = 0.0;
  while (true) { x = std::cos(x); }
}

#ifdef MY_DEBUG
#include "debug_dump.hpp"
#include "backward.hpp"
backward::SignalHandling kSignalHandling;
#else
#define DUMP(...)
#define test_case(...)
#define cerr if(false)cerr
#endif

using namespace std;

template<int kMaxSize, int kMaxValue>
struct SparseIntSet {
  int size_;
  int dense_[kMaxSize];
  int sparse_[kMaxValue + 1];

  SparseIntSet() noexcept: size_(0) {}

  // O(1)
  bool contains(int x) const {
    // May access uninitialized memory, but safe.
    const size_t i = sparse_[x];
    return i < (size_t) size_ and dense_[i] == x;
  }

  // O(1)
  void insert(int x) {
    if (contains(x)) return;
    dense_[size_] = x;
    sparse_[x] = size_++;
  }

  // O(1)
  void erase(int x) {
    const int i = sparse_[x];
    if (i < 0 or i >= size_ or dense_[i] != x) return;
    const auto y = dense_[--size_];
    dense_[i] = y;
    sparse_[y] = i;
  }

  // O(1)
  inline void clear() { size_ = 0; }
  inline int size() const { return size_; }
  inline bool empty() const { return size_ == 0; }

  // O(size)
  template<class F>
  void for_each(F func) {
    for (int i = 0; i < size_; ++i) {
      func(dense_[i]);
    }
  }

  using iterator = int *;
  using const_iterator = const int *;
  iterator begin() { return dense_; }
  const_iterator begin() const { return dense_; }
  iterator end() { return dense_ + size_; }
  const_iterator end() const { return dense_ + size_; }

  // For silencing warnings on accessing uninitialized memory.
  void safe_init() {
    dense_.fill(0);
    sparse_.fill(0);
  }
};
using IntSet = SparseIntSet<200'005, 200'005>;

int msb_log(unsigned x) {
  assert(x != 0);
  return std::numeric_limits<unsigned>::digits - __builtin_clz(x) - 1;
}
int msb_log(Uint x) {
  assert(x != 0);
  return std::numeric_limits<Uint>::digits - __builtin_clzll(x) - 1;
}
template<typename T, typename U = std::make_unsigned_t<T>>
U msb(T x) {
  if (x == 0) return 0;
  return U(1) << msb_log(U(x));
}

pair<int, int> read_input() {
  int x, y;
  cin >> x >> y;
  return {x, y};
}

void write_move(int x, int y) {
  cout << x << ' ' << y << endl;
}

void mirror_strategy(int N, int L, int R) {
  cout << "First" << endl;
  int e = L;
  if (L != R and (N - L) % 2 != 0) ++e;
  int A = (N - e) / 2;
  cout << (A + 1) << ' ' << (N - 2 * A) << endl;
  int B = N - A + 1;
  while (true) {
    auto [x, y] = read_input();
    if (x == 0 and y == 0) {
      exit_();
    }
    if (x == -1 and y == -1) {
      exit_();
    }
    if (x >= B) {
      int gap = x - B;
      write_move(A - gap - y + 1, y);
    } else {
      int gap = A - (x + y - 1);
      write_move(B + gap, y);
    }
  }
}

void nimber_strategy(int N, int L) {
  vector<int> nimber(N + 1, 0);
  for (int n = 1; n <= N; ++n) {
    set<int> gs;
    for (int i = 0; i <= n + 100; ++i) {
      gs.insert(i);
    }
    for (int x = 0; x + L <= n; ++x) {
      int y = n - (x + L);
      gs.erase(nimber[x] ^ nimber[y]);
    }
    assert (not gs.empty());
    nimber[n] = *gs.begin();
  }
  DUMP(nimber);

  set<pair<int, int>> cards;
  cards.insert(pair{1, N});

  auto erase_interval = [&](int x, bool do_assert) {
    auto it = cards.upper_bound({x, kBig<int>});
    if (it == cards.begin()) {
      TLE();
    }
    --it;
    auto [a, k] = *it;
    if (a <= x and x + L <= a + k) {
      cards.erase(it);
      if (x > a) {
        cards.insert(pair{a, x - a});
      }
      int r = a + k - (x + L);
      if (r > 0) {
        cards.insert(pair{x + L, r});
      }
      return;
    }
    if (do_assert) {
      assert(false);
    } else {
      TLE();
    }
  };

  auto play = [&]() {
    int cur_nimber = 0;
    for (auto [a, k]: cards) {
      cur_nimber ^= nimber[k];
    }
    if (cur_nimber == 0) {
      assert(false);
    }
    uint32_t high_bit = msb(cur_nimber);

    for (auto it = cards.begin(); it != cards.end(); ++it) {
      auto [a, k] = *it;
      if (not(nimber[k] & high_bit)) continue;
      int target = nimber[k] ^ cur_nimber;
      for (int x = a; x + L <= a + k; ++x) {
        int p = x - a;
        int q = (a + k) - (x + L);
        int g = nimber[p] ^ nimber[q];
        if (g == target) {
          erase_interval(x, false);
          write_move(x, L);
          return;
        }
      }
    }
    //assert(false);
    TLE();
  };

  if (nimber[N] == 0) {
    cout << "Second" << endl;
  } else {
    cout << "First" << endl;
    play();
  }

  while (true) {
    auto [x, y] = read_input();
    if (x == 0 and y == 0) {
      exit_();
    }
    if (x == -1 and y == -1) {
      exit_();
    }
    if (y != L) {
      assert(false);
    }
    erase_interval(x, false);
    play();
  }
}

int main() {
  int N, L, R;
  cin >> N >> L >> R;
  if (L != R or (N - L) % 2 == 0) {
    mirror_strategy(N, L, R);
  } else {
    nimber_strategy(N, L);
  }
}

Submission Info

Submission Time
Task G - Generalized Subtraction Game
User keijak
Language C++ (GCC 9.2.1)
Score 600
Code Size 5936 Byte
Status AC
Exec Time 177 ms
Memory 35508 KiB

Judge Result

Set Name Sample All
Score / Max Score 0 / 0 600 / 600
Status
AC × 1
AC × 58
Set Name Test Cases
Sample 00_sample_00.txt
All 00_sample_00.txt, 01_l_eq_r_00.txt, 01_l_eq_r_01.txt, 01_l_eq_r_02.txt, 01_l_eq_r_03.txt, 01_l_eq_r_04.txt, 02_l_eq_r_first_00.txt, 02_l_eq_r_first_01.txt, 02_l_eq_r_first_02.txt, 02_l_eq_r_first_03.txt, 02_l_eq_r_first_04.txt, 03_l_eq_r_second_00.txt, 03_l_eq_r_second_01.txt, 03_l_eq_r_second_02.txt, 03_l_eq_r_second_03.txt, 03_l_eq_r_second_04.txt, 03_l_eq_r_second_05.txt, 03_l_eq_r_second_06.txt, 03_l_eq_r_second_07.txt, 03_l_eq_r_second_08.txt, 03_l_eq_r_second_09.txt, 03_l_eq_r_second_10.txt, 03_l_eq_r_second_11.txt, 03_l_eq_r_second_12.txt, 03_l_eq_r_second_13.txt, 03_l_eq_r_second_14.txt, 03_l_eq_r_second_15.txt, 04_random_00.txt, 04_random_01.txt, 04_random_02.txt, 04_random_03.txt, 04_random_04.txt, 04_random_05.txt, 04_random_06.txt, 04_random_07.txt, 04_random_08.txt, 04_random_09.txt, 05_l_plus_1_eq_r_00.txt, 05_l_plus_1_eq_r_01.txt, 05_l_plus_1_eq_r_02.txt, 06_l_plus_2_eq_r_00.txt, 06_l_plus_2_eq_r_01.txt, 06_l_plus_2_eq_r_02.txt, 07_r_small_00.txt, 07_r_small_01.txt, 07_r_small_02.txt, 07_r_small_03.txt, 07_r_small_04.txt, 07_r_small_05.txt, 07_r_small_06.txt, 07_r_small_07.txt, 07_r_small_08.txt, 07_r_small_09.txt, 07_r_small_10.txt, 07_r_small_11.txt, 07_r_small_12.txt, 07_r_small_13.txt, 07_r_small_14.txt
Case Name Status Exec Time Memory
00_sample_00.txt AC 33 ms 35312 KiB
01_l_eq_r_00.txt AC 32 ms 35448 KiB
01_l_eq_r_01.txt AC 33 ms 35448 KiB
01_l_eq_r_02.txt AC 33 ms 35384 KiB
01_l_eq_r_03.txt AC 33 ms 35428 KiB
01_l_eq_r_04.txt AC 49 ms 35488 KiB
02_l_eq_r_first_00.txt AC 32 ms 35464 KiB
02_l_eq_r_first_01.txt AC 123 ms 35364 KiB
02_l_eq_r_first_02.txt AC 30 ms 35492 KiB
02_l_eq_r_first_03.txt AC 33 ms 35372 KiB
02_l_eq_r_first_04.txt AC 120 ms 35464 KiB
03_l_eq_r_second_00.txt AC 106 ms 35436 KiB
03_l_eq_r_second_01.txt AC 102 ms 35504 KiB
03_l_eq_r_second_02.txt AC 91 ms 35328 KiB
03_l_eq_r_second_03.txt AC 91 ms 35432 KiB
03_l_eq_r_second_04.txt AC 71 ms 35456 KiB
03_l_eq_r_second_05.txt AC 71 ms 35428 KiB
03_l_eq_r_second_06.txt AC 160 ms 35388 KiB
03_l_eq_r_second_07.txt AC 159 ms 35404 KiB
03_l_eq_r_second_08.txt AC 73 ms 35384 KiB
03_l_eq_r_second_09.txt AC 78 ms 35444 KiB
03_l_eq_r_second_10.txt AC 34 ms 35488 KiB
03_l_eq_r_second_11.txt AC 134 ms 35472 KiB
03_l_eq_r_second_12.txt AC 36 ms 35412 KiB
03_l_eq_r_second_13.txt AC 36 ms 35384 KiB
03_l_eq_r_second_14.txt AC 46 ms 35352 KiB
03_l_eq_r_second_15.txt AC 159 ms 35508 KiB
04_random_00.txt AC 33 ms 35428 KiB
04_random_01.txt AC 38 ms 35344 KiB
04_random_02.txt AC 30 ms 35408 KiB
04_random_03.txt AC 38 ms 35428 KiB
04_random_04.txt AC 28 ms 35448 KiB
04_random_05.txt AC 33 ms 35372 KiB
04_random_06.txt AC 38 ms 35472 KiB
04_random_07.txt AC 33 ms 35420 KiB
04_random_08.txt AC 28 ms 35404 KiB
04_random_09.txt AC 32 ms 35444 KiB
05_l_plus_1_eq_r_00.txt AC 32 ms 35460 KiB
05_l_plus_1_eq_r_01.txt AC 34 ms 35456 KiB
05_l_plus_1_eq_r_02.txt AC 35 ms 35424 KiB
06_l_plus_2_eq_r_00.txt AC 29 ms 35380 KiB
06_l_plus_2_eq_r_01.txt AC 34 ms 35332 KiB
06_l_plus_2_eq_r_02.txt AC 34 ms 35420 KiB
07_r_small_00.txt AC 52 ms 35380 KiB
07_r_small_01.txt AC 44 ms 35488 KiB
07_r_small_02.txt AC 53 ms 35468 KiB
07_r_small_03.txt AC 49 ms 35348 KiB
07_r_small_04.txt AC 49 ms 35396 KiB
07_r_small_05.txt AC 42 ms 35416 KiB
07_r_small_06.txt AC 39 ms 35420 KiB
07_r_small_07.txt AC 43 ms 35404 KiB
07_r_small_08.txt AC 42 ms 35464 KiB
07_r_small_09.txt AC 177 ms 35432 KiB
07_r_small_10.txt AC 42 ms 35336 KiB
07_r_small_11.txt AC 41 ms 35424 KiB
07_r_small_12.txt AC 38 ms 35360 KiB
07_r_small_13.txt AC 37 ms 35496 KiB
07_r_small_14.txt AC 39 ms 35424 KiB