結果
問題 | No.879 Range Mod 2 Query |
ユーザー | テナガザル |
提出日時 | 2024-08-04 03:38:08 |
言語 | C++23 (gcc 12.3.0 + boost 1.83.0) |
結果 |
WA
|
実行時間 | - |
コード長 | 4,589 bytes |
コンパイル時間 | 1,445 ms |
コンパイル使用メモリ | 118,344 KB |
実行使用メモリ | 16,360 KB |
最終ジャッジ日時 | 2024-08-04 03:38:18 |
合計ジャッジ時間 | 8,683 ms |
ジャッジサーバーID (参考情報) |
judge1 / judge5 |
(要ログイン)
テストケース
テストケース表示入力 | 結果 | 実行時間 実行使用メモリ |
---|---|---|
testcase_00 | AC | 2 ms
6,816 KB |
testcase_01 | WA | - |
testcase_02 | WA | - |
testcase_03 | WA | - |
testcase_04 | WA | - |
testcase_05 | WA | - |
testcase_06 | WA | - |
testcase_07 | WA | - |
testcase_08 | WA | - |
testcase_09 | WA | - |
testcase_10 | WA | - |
testcase_11 | WA | - |
testcase_12 | WA | - |
testcase_13 | WA | - |
testcase_14 | WA | - |
testcase_15 | WA | - |
testcase_16 | WA | - |
testcase_17 | WA | - |
testcase_18 | WA | - |
testcase_19 | AC | 529 ms
15,840 KB |
testcase_20 | AC | 516 ms
15,948 KB |
testcase_21 | AC | 572 ms
15,744 KB |
ソースコード
#include <iostream> #include <vector> #include <stack> #include <algorithm> using namespace std; template <typename T, typename X> class LazySegTree { private: const T et; const X ex; int num; std::vector<T> dat; std::vector<X> lazy; T (*const eval)(const T, const T) {}; T (*const fa)(const T, const X) {}; X (*const fm)(const X, const X) {}; X (*const fp)(const X, int) {}; public: LazySegTree(std::vector<T> &v, T Et, X Ex, T (*valcal)(T, T), T (*lazyupdate)(T, X), X (*lazypropagation)(X, X), X (*rangelazy)(X, int)) : et(Et), ex(Ex), eval(valcal), fa(lazyupdate), fm(lazypropagation), fp(rangelazy) { int siz = static_cast<int>(v.size()); for (num = 1; num < siz; num <<= 1); dat = std::vector<T> (2 * num - 1, et); lazy = std::vector<X> (2 * num - 1, ex); for (int i = 0; i < siz; ++i) dat[i + num - 1] = v[i]; for (int i = num - 2; i >= 0; --i) dat[i] = eval(dat[i * 2 + 1], dat[i * 2 + 2]); } LazySegTree(int n, T Et, X Ex, T (*valcal)(T, T), T (*lazyupdate)(T, X), X (*lazypropagation)(X, X), X (*rangelazy)(X, int)) : et(Et), ex(Ex), eval(valcal), fa(lazyupdate), fm(lazypropagation), fp(rangelazy) { for (num = 1; num < n; num <<= 1); dat = std::vector<T> (2 * num - 1, et); lazy = std::vector<X> (2 * num - 1, ex); } //update [left,right) void rangeupdate(int left, int right, X val) { std::stack<std::pair<int, int>> st; std::stack<int> s; for (st.push({0, num}); !st.empty();) { auto v = st.top(); st.pop(); int now = (num + v.first) / (v.second - v.first) - 1; lazyupdate(now, v.second - v.first); if (left <= v.first && v.second <= right) { lazy[now] = fm(lazy[now], val); lazyupdate(now, v.second - v.first); } else if (!(v.second <= left || right <= v.first)) { st.push({(v.first + v.second) / 2, v.second}); st.push({v.first, (v.first + v.second) / 2}); s.push(now); } } while (!s.empty()) { int index = s.top(); dat[index] = eval(dat[2 * index + 1], dat[2 * index + 2]); s.pop(); } } //get value [left,right) T getval(int left, int right) { std::stack<std::pair<int, int>> s; T ans = et; for (s.push({0, num}); !s.empty();) { auto v = s.top(); s.pop(); int now = (num + v.first) / (v.second - v.first) - 1; lazyupdate(now, v.second - v.first); if (left <= v.first && v.second <= right) ans = eval(ans, dat[now]); else if (!(v.second <= left || right <= v.first)) { s.push({(v.first + v.second) / 2, v.second}); s.push({v.first, (v.first + v.second) / 2}); } } return ans; } //get value [id] T getval(int id) {return getval(id, id + 1);} private: void lazyupdate(int index, int len) { if (lazy[index] == ex) return; if (index < num - 1) { lazy[index * 2 + 1] = fm(lazy[index * 2 + 1], lazy[index]); lazy[index * 2 + 2] = fm(lazy[index * 2 + 2], lazy[index]); } dat[index] = fa(dat[index], fp(lazy[index], len)); lazy[index] = ex; } }; int main() { struct dat { int cnt0, cnt1, len; long long sum; dat(int c0, int c1, int l, long long v) : cnt0(c0), cnt1(c1), len(l), sum(v) {} }; auto eval = [](dat a, dat b) -> dat {return dat(a.cnt0 + b.cnt0, a.cnt1 + b.cnt1, a.len + b.len, a.sum + b.sum);}; auto fa = [](dat a, pair<bool, long long> b) -> dat { if (b.first) a.sum = a.cnt1; a.sum += b.second * a.len; if (b.second % 2) swap(a.cnt1, a.cnt0); return a; }; auto fm = [](pair<bool, long long> a, pair<bool, long long> b) -> pair<bool, long long> { if (b.first) a.second = 0; a.first |= b.first; a.second += b.second; return a; }; auto fp = [](pair<bool, long long> a, int b) -> pair<bool, long long> { return a; }; int n, q; cin >> n >> q; vector<dat> v; dat e(1, 0, 1, 0); for (int i = 0; i < n; ++i) { int a; cin >> a; v.push_back(dat((a + 1) % 2, a % 2, 1, a)); } LazySegTree<dat, pair<bool, long long>> lsg(v, e, {false, 0}, eval, fa, fm, fp); while (q--) { int t; cin >> t; if (t == 1) { int l, r; cin >> l >> r; --l; lsg.rangeupdate(l, r, {true, 0}); } else if (t == 2) { int l, r, x; cin >> l >> r >> x; --l; lsg.rangeupdate(l, r, {false, x}); } else if (t == 3) { int l, r; cin >> l >> r; --l; auto res = lsg.getval(l, r); cout << res.sum << endl; } } }