順位表: https://icpcsec.firebaseapp.com/standings/
4 完で 48 位で予選通過です。うおおお!!!
第一志望の研究室の教授に相談したら研究室で ICPC に参加してよいことになりました。 また PC やディスプレイやマウスやプリンターも使っていいよと言ってもらえとても助かりました。
ICPC 開始 30 分前に研究室配属の結果が出て、無事そこの研究室への配属が確定しました。
A をえくとくんに投げて、B をチラ見し、面倒そうなので C, D, E に目を通しました。
C を Ackvy くんと考えます。市松模様を書いて黒いところは固定したまま、それ以外を動かすとよさそうと話して、偶数の時は上下左右分割し斜めに swap すれば良いね、奇数のときはいい感じに反転したりしてから swap すればいいねという話になります。気づいたらえくとくんが B まで通していました。
C の実装が嫌なのでえくとくんに方針を伝えて投げました。怖いので手元でジャッジを書いたほうが良さそうだよねと話してジャッジも書いてもらいました。すべての実装を投げました。その間に Ackvy くんと E を考えますが上手く方針が立ちません。貪欲にできないかなぁ~みたいなことを話したのですが、上手く行かなさそうでした。
C がまだ通っていなかったので見に行きます。手元で回して偶数の時は OK ですが奇数のときはインデックス回りが壊れていそうだったので変わって僕が書くことになりました。なんとか書いたのですが 0 が出現したりで発狂していました。修正したのですが、手元で回すと WA になってしまいました。 よく見ると奇数のなかでも のときに壊れていました。Ackvy くんと考察をし直します。 真ん中の列をいい感じに swap するといいねぇという話になり実装して提出します。WA ります。え? 僕の実装が間違っていました。ごめん… 修正して投げて AC です。この時点で残りが 30 分で、予選落ちたな…と絶望ぎみでした。
D は Ackvy くんが「これって 8 以下にできませんか?」という天才発言をしたことにより、dfs しながら枝刈り全探索すればよくない?という話になります。残りが 30 分なのでめちゃめちゃ急いで実装します。
#include <bits/stdc++.h>using namespace std;
using ll = long long;#define rep(i, n) for (ll i = 0; i < (n); i++)
bool solve() { ll N; cin >> N; if (N == 0) return false; string S; cin >> S; ll ans = 8;
vector<ll> v = {}; ll sum = 0; auto check = [&]() -> bool { ll m = v.size(); set<ll> s; rep(msk, 1 << m) { ll add = 0; rep(j, m) { if ((msk >> j) & 1) add += v[j]; } s.insert(add); } rep(i, N + 1) if (S[i] == 'o') { if (s.count(i) == 0) return false; } return true; };
auto dfs = [&](auto&& self) { if (sum == N) { if (check()) { ans = min(ans, (ll)v.size()); } return; } if (v.size() >= ans) return; ll b = (v.empty() ? 1 : v.back()); for (ll add = b; sum + add <= N; add++) { v.push_back(add); sum += add; self(self); sum -= add; v.pop_back(); } };
dfs(dfs);
cout << ans << endl; return true;}
int main() { while (solve()) ;}
実行したらちょっと時間がかかってううううう…となりましたが、1 分くらい待ったら無事終わりました。投げたら AC でした。わーい! C を通してから 12 分くらいで D を通しました、これにより予選通過が確定しました。天才すぎ!!
近くのお好み焼き屋さんにいきました。おいしかったです!
予選通過できて本当に良かったです。去年から順位が上がっていていい感じです。来年はもっと上に行けるといいなぁ…