長さNの01からなる文字列がs与えられる。次の条件を満たすの文字列tを見つけたい。LISの長さが同じtに含まれる0の数が上二つの条件を満たす中で最大メモ1まず、先頭と末尾以外の文字について、文字を変更できるパターンを考える。000->010:後ろ2文字を取ってきたときに不適001->011:少なくともこの3文字からはどのように部分文字列を取ってきても条件に違反しない010->000:後ろ2文字を取ってきたときに不適011->001:少なくともこの3文字からはどのように部分文字列を取ってきても条件に違反しない100->110:後ろ2文字を取ってきたときに不適101->111:3文字を取ってきたときに不適110->100:先頭2文字を取ってきたときに不適111->101:先頭2文字を取ってきたときに不適また、一気に複数文字変更することを考えたときに、0.....0、1.....1以外の塊を変更させるのは、01若しくは10の部分を取ってきたときに不適であることがわかるため、複数文字変更のパターンは0.....0->1.....1か1.....1->0.....0だが、それらは1文字変更を何回か繰り返したものとみなせるので1文字変更のみを考える。001->011と011->001は逆操作であり、0の数を最大化したいことを考えるとあり得る操作は011->001のみになる。メモ2文字列sの先頭に0を、末尾に1を付けて考えてよい。これは、新たな先頭を含んだ文字列は常にLISの長さが1長くなり、新たな末尾を含んだ文字列は常にLISの長さが1長くなるからである。これによって、もとのsのすべての要素が、前の要素も後ろの要素も持つようになり、メモ1の内容を適用できる。先頭が1という条件のLISの長さとなるようなl,rが存在する場合である。二つ目の条件はよく見ると左右に分割することができることが分かる。両辺が等しくないときは左側、右側のどちらかが等しくないことが必要だからである。先頭が1という条件のLISの長さと表せる。メモ4左から貪欲に変更していくことができると非常にうれしいので、貪欲で良いことを証明したい。LISの長さは長くなる、変わらない、短くなるのどれもあり得るため、変更できない条件を見ると左側の変更によって、右側の変更を妨げない、もしくは促進する。右側の条件を考えると、影響がないため、左側の変更によって、右側の変更を妨げない。よって、左から貪欲に変更していくことが可能である。右側から変更していくと妨げる場合があるので注意である。今見ている文字の左側の0で終わる部分文字列のLISと1で終わる部分文字列のLISの長さの差、右側の0で始まる部分文字列のLISと1で始まる部分文字列のLISの長さの差が求められれば良い。文字が2種類なのですべて持っておきながらLISの長さを求めることが可能である。迷路君とkenさんとチームを組んで参戦。読者になる検索リンクはてなブログブログをはじめる週刊はてなブログはてなブログPro最新記事AtCoderで灰色になりすますまでにやったことチーム練(2016バンコク)CivilizationV紹介チーム練(2018ソウル)チーム練(2018ジャカルタ)月別アーカイブはてなブログをはじめよう!olpheさんは、はてなブログを使っています。ブログを報告するスターをつけました引用をストックしましたストック一覧を見る閉じる引用するにはまずログインしてくださいログイン閉じる引用をストックできませんでした。再度お試しください閉じる限定公開記事のため引用できません。