제출 #882809

#제출 시각아이디문제언어결과실행 시간메모리
882809MilosMilutinovicChorus (JOI23_chorus)C++14
87 / 100
7015 ms61248 KiB
#include <bits/stdc++.h> using namespace std; struct line { long long k, n; int f; void init() { k = 0; n = (long long) 1e18; f = 0; } long long val(long long x) { return k * x + n; } }; const int MAX = 5e6; line li[MAX]; int ls[MAX], rs[MAX], tsz, root; void Update(int& x, int l, int r, line ln) { if (!x) { x = ++tsz; li[x].init(); } int mid = l + r >> 1; if (li[x].val(mid) > ln.val(mid) || (ln.val(mid) == li[x].val(mid) && ln.f < li[x].f)) { swap(li[x], ln); } if (l == r) { return; } if (ln.val(l) < li[x].val(l)) { Update(ls[x], l, mid, ln); } else { Update(rs[x], mid + 1, r, ln); } } pair<long long, int> Query(int x, int l, int r, int i) { if (!x) { return make_pair((long long) 1e18, 0); } if (l == r) { return make_pair(li[x].val(i), li[x].f); } int mid = l + r >> 1; if (i <= mid) { return min(Query(ls[x], l, mid, i), make_pair(li[x].val(i), li[x].f)); } else { return min(Query(rs[x], mid + 1, r, i), make_pair(li[x].val(i), li[x].f)); } } void clear_seg() { while (tsz > 0) { ls[tsz] = 0; rs[tsz] = 0; li[tsz].init(); tsz -= 1; } root = 0; } int main() { ios::sync_with_stdio(false); cin.tie(0); int n, k; cin >> n >> k; string s; cin >> s; vector<int> a, b; for (int i = 0; i < 2 * n; i++) { if (s[i] == 'A') { a.push_back(i); } else { b.push_back(i); } } vector<int> ia(2 * n); for (int i = 0; i < n; i++) { ia[a[i]] = i + 1; } vector<long long> pref(2 * n); for (int i = 0; i < 2 * n; i++) { if (i > 0) { pref[i] = pref[i - 1]; } pref[i] += (s[i] == 'A' ? 1 : 0); } vector<int> ib(2 * n); for (int i = 0; i < n; i++) { ib[b[i]] = pref[b[i]]; } for (int i = 0; i < n; i++) { if (i > 0) { pref[i] = pref[i - 1]; } else { pref[i] = 0; } pref[i] += ib[b[i]]; } auto Solve = [&](long long mid) { const long long inf = (long long) 1e18; vector<pair<long long, int>> dp(n + 1, {inf, 0}); dp[0] = {0, 0}; int ptr = -1; multiset<pair<long long, int>> st; clear_seg(); for (int i = 0; i < n; i++) { st.insert(dp[i]); while (ptr + 1 <= i && ia[a[i]] >= ib[b[ptr + 1]]) { ptr += 1; line cur; cur.k = -ptr; cur.n = dp[ptr].first + (ptr == 0 ? 0 : pref[ptr - 1]) + mid; cur.f = dp[ptr].second; Update(root, 0, n, cur); st.erase(st.find(dp[ptr])); } if (!st.empty()) { pair<long long, int> val = *st.begin(); dp[i + 1] = min(dp[i + 1], {val.first + mid, val.second + 1}); } if (ptr != -1) { pair<long long, int> val = Query(root, 0, n, ia[a[i]]); dp[i + 1] = min(dp[i + 1], {val.first + ia[a[i]] * 1LL * (ptr + 1) - pref[ptr], val.second + 1}); } } return dp[n]; }; long long low = 0, high = 1e12, p = 0; while (low <= high) { long long mid = low + high >> 1; pair<long long, int> res = Solve(mid); if (res.second <= k) { p = mid; high = mid - 1; } else { low = mid + 1; } } pair<long long, int> res = Solve(p); cout << res.first - p * k << '\n'; return 0; }

컴파일 시 표준 에러 (stderr) 메시지

chorus.cpp: In function 'void Update(int&, int, int, line)':
chorus.cpp:28:15: warning: suggest parentheses around '+' inside '>>' [-Wparentheses]
   28 |   int mid = l + r >> 1;
      |             ~~^~~
chorus.cpp: In function 'std::pair<long long int, int> Query(int, int, int, int)':
chorus.cpp:49:15: warning: suggest parentheses around '+' inside '>>' [-Wparentheses]
   49 |   int mid = l + r >> 1;
      |             ~~^~~
chorus.cpp: In function 'int main()':
chorus.cpp:136:25: warning: suggest parentheses around '+' inside '>>' [-Wparentheses]
  136 |     long long mid = low + high >> 1;
      |                     ~~~~^~~~~~
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...