結果
問題 |
No.3122 Median of Medians of Division
|
ユーザー |
|
提出日時 | 2025-04-20 05:35:21 |
言語 | C++17 (gcc 13.3.0 + boost 1.87.0) |
結果 |
TLE
|
実行時間 | - |
コード長 | 5,533 bytes |
コンパイル時間 | 2,596 ms |
コンパイル使用メモリ | 215,584 KB |
実行使用メモリ | 124,516 KB |
最終ジャッジ日時 | 2025-04-20 05:35:33 |
合計ジャッジ時間 | 11,352 ms |
ジャッジサーバーID (参考情報) |
judge5 / judge2 |
(要ログイン)
ファイルパターン | 結果 |
---|---|
sample | -- * 1 |
other | TLE * 1 -- * 39 |
ソースコード
#include <bits/stdc++.h> using namespace std; struct Fenwick2D { int M; vector<vector<int>> ys; vector<vector<int>> bit; Fenwick2D(int _M): M(_M), ys(_M+1) {} // register (value idx, position) for structure building void fake_update(int v, int pos) { for(int i = v; i <= M; i += i & -i) { ys[i].push_back(pos); } } // initialize internal BIT arrays after all fake_update calls void init() { bit.resize(M+1); for(int i = 1; i <= M; i++) { auto &v = ys[i]; sort(v.begin(), v.end()); v.erase(unique(v.begin(), v.end()), v.end()); bit[i].assign(v.size()+1, 0); } } // point update: add delta at (value idx = v, position = pos) void update(int v, int pos, int delta) { for(int i = v; i <= M; i += i & -i) { int idx = int(lower_bound(ys[i].begin(), ys[i].end(), pos) - ys[i].begin()) + 1; for(int j = idx; j < (int)bit[i].size(); j += j & -j) { bit[i][j] += delta; } } } // prefix sum for values <= v, positions <= pos int query(int v, int pos) const { int res = 0; for(int i = v; i > 0; i -= i & -i) { int idx = int(upper_bound(ys[i].begin(), ys[i].end(), pos) - ys[i].begin()); for(int j = idx; j > 0; j -= j & -j) { res += bit[i][j]; } } return res; } // sum over values in [v_lo, v_hi], positions in [l, r] int range_query(int v_lo, int v_hi, int l, int r) const { if(v_lo > v_hi || l > r) return 0; int a = query(v_hi, r) - query(v_hi, l - 1); int b = query(v_lo - 1, r) - query(v_lo - 1, l - 1); return a - b; } }; int main() { ios::sync_with_stdio(false); cin.tie(NULL); int N, Q; cin >> N >> Q; vector<int> A(N+2); for(int i = 1; i <= N; i++) cin >> A[i]; struct Query { int type, i, x, l, r; }; vector<Query> queries(Q); // collect all values for compression and per-position possible values vector<int> all_vals; all_vals.reserve(N + Q + 5); vector<vector<int>> pos_vals(N+2); for(int i = 1; i <= N; i++) { pos_vals[i].push_back(A[i]); all_vals.push_back(A[i]); } for(int qi = 0; qi < Q; qi++) { int t; cin >> t; queries[qi].type = t; if(t == 1) { cin >> queries[qi].i >> queries[qi].x; all_vals.push_back(queries[qi].x); pos_vals[queries[qi].i].push_back(queries[qi].x); } else { cin >> queries[qi].l >> queries[qi].r; } } // compress all values sort(all_vals.begin(), all_vals.end()); all_vals.erase(unique(all_vals.begin(), all_vals.end()), all_vals.end()); int M = all_vals.size(); auto comp = [&](int x) { return int(lower_bound(all_vals.begin(), all_vals.end(), x) - all_vals.begin()) + 1; }; // build Fenwick2D structure Fenwick2D fw(M); // fake updates for element events for(int i = 1; i <= N; i++) { auto &pv = pos_vals[i]; sort(pv.begin(), pv.end()); pv.erase(unique(pv.begin(), pv.end()), pv.end()); for(int v : pv) { fw.fake_update(comp(v), i); } } // fake updates for pair events (i, i+1) for(int i = 1; i < N; i++) { vector<int> uv = pos_vals[i]; uv.insert(uv.end(), pos_vals[i+1].begin(), pos_vals[i+1].end()); sort(uv.begin(), uv.end()); uv.erase(unique(uv.begin(), uv.end()), uv.end()); for(int v : uv) { fw.fake_update(comp(v), i); } } fw.init(); // initial population of weights // element weight = +2 for(int i = 1; i <= N; i++) { fw.update(comp(A[i]), i, +2); } // pair weight = +1 for(int i = 1; i < N; i++) { int pv = max(A[i], A[i+1]); fw.update(comp(pv), i, +1); } // process queries for(auto &q : queries) { if(q.type == 1) { int idx = q.i; int old = A[idx]; int neu = q.x; // element update fw.update(comp(old), idx, -2); fw.update(comp(neu), idx, +2); // pair (idx-1, idx) if(idx > 1) { int oldp = max(A[idx-1], old); int newp = max(A[idx-1], neu); fw.update(comp(oldp), idx-1, -1); fw.update(comp(newp), idx-1, +1); } // pair (idx, idx+1) if(idx < N) { int oldp = max(old, A[idx+1]); int newp = max(neu, A[idx+1]); fw.update(comp(oldp), idx, -1); fw.update(comp(newp), idx, +1); } A[idx] = neu; } else { int l = q.l, r = q.r; int len = r - l + 1; // total weight in [1..M] values, positions [l..r] int total = fw.range_query(1, M, l, r); // binary search on value-axis int lo = 1, hi = M, ans_idx = 1; while(lo <= hi) { int mid = (lo + hi) >> 1; int low = fw.range_query(1, mid-1, l, r); int w = total - low; if(w > len) { ans_idx = mid; lo = mid + 1; } else { hi = mid - 1; } } cout << all_vals[ans_idx-2] << '\n'; } } return 0; }