コンテストページ: https://atcoder.jp/contests/abc281
コンテスト中AC: A〜D
コンテスト後にEをAC(自力)
D - Max Multiple
が小さい
- 倍数は
の情報があれば良い
これらからDPだろうと判断しました。
情報としては、
- 何項目までを考慮したか
- 選んだ項の総和の
- 選んだ項の個数
が分かればよいので、
の
項目までを考慮し、選んだ項の総和の
が
であり、選んだ項の個数が
であるときの選んだ項の総和の最大値
遷移は以下のとおりです。
を選ばない場合
を選ぶ場合
初期値は、としておき、その他は
などで埋めておけばよいです。
なお、が
の場合は遷移元としないようにする必要があることに注意します。
答えは、です。
提出コード: Submission #37160568 - AtCoder Beginner Contest 281
E - Least Elements
コンテスト中multisetで解こうとして結局だめでした。コンテスト後にWavelet Matrixで解けました。
から
までを昇順に並べた数列を
とします。
の先頭
項の和を
とします。
について、
を削除し、
を追加した場合に、
から
にどのように変化したかがわかれば、
から変化分を増減させることで、
を計算できます。
これを考える時、がそれぞれ
の
番目以内かそうでないかの4通りを考えれば良いです。
具体的に説明します。
が
の
番目以内
この時、の分、和は減少します。
が
の
番目以内
が削除され、
が挿入することを考えると、削除されて空いた箇所に左詰めまたは右詰めで各要素が移動し、
が挿入されたと考えることができます。
このケースでは、新たにが
番目以内となってその分の和が増加するので、
と計算できます。が
の
番目より後ろ
が削除されて空いた箇所にそれより後ろの要素が左詰めされて、
が挿入されます。
このケースでは、における
番目の要素が
で新たに
番目となり、この分の和が増加するので、これを
とおけば、
と計算できます。
が
の
番目より後ろ
このケースでは、による和の減少はありません。
が
の
番目以内
が挿入されると、
の削除によって空いた箇所に右詰めされるように動きます。 このケースでは、新たに
が
番目以内となってその分の和が増加し、
で
番目だった要素が
における
番目となって、この分が減少するので、
と計算できます。が
の
番目より後ろ
は和に影響しないので、
となります。
を全て記録することは
の領域が必要となるので、不可能だと思います。また、仮にそれが可能だとしても、C++のvectorなら昇順ソートが毎回必要ですし、multisetでは何番目の要素かを得るのに時間がかかります。
そこで、Wavelet Matrixを使います。Wavelet Matrixはで構築し、
で指定区間の任意のx番目に小さい要素を得ることが可能です。(但し、
は
に含まれる要素の最大値)
これで、で解くことができます。