
https://atcoder.jp/contests/abc417/tasks/abc417_batcoder.jp
配点: 200 点 / 実行時間制限: 2 sec / メモリ制限: 1024 MB / Difficulty: 41 / NoviSteps: 6Q
問題概要
長さ の広義単調増加整数列
が与えられる。この整数列に対して、
回の操作を行う。
回目の操作では、次の操作を行う。
- 数列
が
を要素として持つならば、そのような要素を1つ選び削除する。そのような要素が存在しないならば何もしない。
回の操作を行った後の
を求めよ。
制約
- 入力はすべて整数
考察
は単調増加数列なので、
の位置(正確には
以上の要素の中で最小のもののイテレータ)は二分探索できる。
位置が特定出来たら、そのイテレータが を指しているかをチェックして、
erase
関数で実際に要素を削除すればよい。
計算量は となる。
実装例
#include <bits/stdc++.h> using namespace std; #define all(x) (x).begin(), (x).end() #define rep(i, start, end) for (auto i = (start); (i) < (end); (i)++) // ======================================== // int main() { int N, M; cin >> N >> M; vector<int> A(N), B(M); rep(i, 0, N) cin >> A[i]; rep(i, 0, M) cin >> B[i]; rep(i, 0, M) { auto itr = lower_bound(all(A), B[i]); if (itr != A.end() && *itr == B[i]) { A.erase(itr); } } for (auto &&x : A) { cout << x << ' '; } cout << endl; }
https://atcoder.jp/contests/abc417/submissions/68464959atcoder.jp
実装時間: 5分
コメント
の制約が小さいので、愚直に二重ループを使ってもいいし、
multiset
を使っても簡単に解けそう。