geam1113’s diary

主にAtcoderのコンテストの備忘録を書きます。AtCoder緑と水色を行ったり来たりしています。

AtCoder Beginner Contest 267 参加記録

コンテストページ:https://atcoder.jp/contests/abc267

コンテスト中AC: A〜D
コンテスト中にもう少しのところでACできなかったEについてコンテスト後に解けたので書きます。

E - Erasing Verticles 2

とり得る値の最小値を求める問題では、二分探索できないか疑います。今回の問題の場合、

  • コストをX以下にすることは可能か?

という問題を考えると、あるコスト以下は全て可能で、それより大きいコストは全て不可能という境界が存在することが言えます。

後は、コストXを定めたときに、この問題について高速に判定できればよいです。

判定方法について考えます。

コストX以下の頂点があればとにかく消した方がよいです。なぜなら、そうすることでその頂点と隣接する頂点のコストを減らすことができるからです。

というわけで、以下の貪欲法が考えられます。

未削除の頂点のうち、コストX以下の頂点を1つ選び、削除する。削除した頂点と隣接する頂点のコストを減らす。これを削除可能な頂点が無くなるまで繰り返す。

この貪欲法について、例えば、削除対象を毎回全頂点から選び出しているだけでもO(N^2)になってしまいます。

ある頂点を削除した時、次に削除対象となる可能性があるのは、その頂点と隣接する頂点だけです。
従って、削除可能な頂点集合Sを管理することで、以下のように処理できます。

頂点を1つも削除していない初期状態で、削除コストがX以下の頂点をSに追加する。その後、Sが空になるまで以下を繰り返す。

Sから頂点を1つ選び、削除する。
削除した頂点に隣接する頂点のコストを減らし、X以下ならSに追加する。

Sが空になった時点で、全ての頂点が削除されていれば、達成可能です。そうでないなら、不可能です。

この方法は、すべての頂点のN回の削除処理において、頂点を削除した時にその頂点から出る辺を1回ずつ辿るので、辺を辿るのは合計2M回となります。
よって、O(N+M)です(多分)。

これにより、高速に判定できることがわかりました。

従って、初期状態でのコストの最大値をC_{max}とすれば、元の問題をO((N+M)log{C_{max}})で解くことができます。

コストが最大となるのは、おそらく全ての頂点に10^9が書かれた場合の完全グラフだと思われます。
その場合でも2\times 10^{14}は超えないはずなので、二分探索も十分高速です。

また、コストの下限は0になることに気をつけなければいけません(これに気づけず、コンテスト中にACできませんでした)。

Submission #34576881 - NEC Programming Contest 2022 (AtCoder Beginner Contest 267)