Aslanov01

SQRT-decomposition with add/del/get operations

Feb 4th, 2024 (edited)
737
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 1.75 KB | Source Code | 0 0
  1. int sz[N];
  2. vector <pii> mn[N];
  3. vector <vector <pii>> g[N];
  4. void fill_v(int id, int block) {
  5.     while (sz(g[id]) <= block)g[id].pb({});
  6.     while (sz(mn[id]) <= block)mn[id].pb({inf, inf});
  7. }
  8. void build(int id) {
  9.     vector <pii> vec;
  10.     for (int block = 0;block < sz(g[id]);block++) {
  11.         for (auto val : g[id][block])vec.pb(val);
  12.     }
  13.     g[id].clear(), mn[id].clear();
  14.     for (int i = 0;i < sz(vec);i++) {
  15.         int block = i / K;
  16.         fill_v(id, block);
  17.         g[id][block].pb(vec[i]);
  18.         if (i % K == 0)mn[id].pb(vec[i]);
  19.     }
  20. }
  21. bool bigger(pii val, pii x) {
  22.     return (val.x > x.x) || (val.x == x.x && val.y >= x.y);
  23. }
  24. pii get(pii val, int id) {
  25.     int b = 0;
  26.     fill_v(id, b + 1);
  27.     while (b + 1 < sz(mn[id]) && bigger(val, mn[id][b + 1]))b++;
  28.     int pos = 0;
  29.     while (pos < sz(g[id][b]) && bigger(val, g[id][b][pos]))pos++;
  30.     return {b, pos};
  31. }
  32. void add(pii val, int id) {
  33.     int block, pos;
  34.     tie(block, pos) = get(val, id);
  35.     vector <pii> vals;
  36.     fill_v(id, block);
  37.     int cnt = sz(g[id][block]) - pos;
  38.     while (cnt--)vals.pb(g[id][block].back()), g[id][block].pop_back();
  39.     mn[id][block] = min(mn[id][block], val);
  40.     g[id][block].pb(val), sz[id]++;
  41.     while (!vals.empty())g[id][block].pb(vals.back()), vals.pop_back();
  42.     if (sz(g[id][block]) > 2 * K)build(id);
  43. }
  44. void del(pii val, int id) {
  45.     int block, pos;
  46.     tie(block, pos) = get(val, id);
  47.     vector <pii> vals;
  48.     fill_v(id, block);
  49.     int cnt = sz(g[id][block]) - pos;
  50.     while (cnt--)vals.pb(g[id][block].back()), g[id][block].pop_back();
  51.     if (!g[id][block].empty())g[id][block].pop_back(), sz[id]--;
  52.     while (!vals.empty())g[id][block].pb(vals.back()), vals.pop_back();
  53.     if (sz(g[id][block]) == 0)build(id);
  54. }
Advertisement
Add Comment
Please, Sign In to add comment