[洛谷1383]高级打字机 题解
生活随笔
收集整理的這篇文章主要介紹了
[洛谷1383]高级打字机 题解
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
題解
這道題一看就珂以用主席樹啊
這是一道神奇的題目,那么我們先敲一個主席樹,然后維護一個數組len,表示下一次應該在len + 1插入,
之后對于T操作,在上一個版本的len + 1上直接執行插入
對于Q操作,直接查詢
對于U操作,直接找到對應版本復制即可
rt[rt_num] = rt[((rt_num - num - 1) > 0 ? (rt_num - num - 1) : 0)];
ls[rt_num] = ls[((rt_num - num - 1) > 0 ? (rt_num - num - 1) : 0)], rs[rt_num] = rs[((rt_num - num - 1) > 0 ? (rt_num - num - 1) : 0)];
len[rt_num] = len[rt_num - num - 1]; 代碼
#include <cstdio>
#include <iostream>
#define ll long longusing namespace std;ll read(){ll x = 0; int zf = 1; char ch = ' ';while (ch != '-' && (ch < '0' || ch > '9')) ch = getchar();if (ch == '-') zf = -1, ch = getchar();while (ch >= '0' && ch <= '9') x = x * 10 + ch - '0', ch = getchar(); return x * zf;
}int s[20000005];
int ls[20000005], rs[20000005];
int len[20000005];
int rt[20000005], pre[20000005];
int tot;inline void a(int pos){s[pos] = s[ls[pos]] + s[rs[pos]];
}inline int getNew(){return (++tot);
}void build(int pos, int l, int r){if (l == r){if (pos > tot)tot = pos;s[pos] = 0;return ;}int mid = (l + r) >> 1;ls[pos] = pos << 1, rs[pos] = (pos << 1) + 1;build(pos << 1, l, mid);build((pos << 1) + 1, mid + 1, r);a(pos);
}int query(int pos, int l, int r, int k){if (l == r)return s[pos];int mid = (l + r) >> 1;if (k <= mid)return query(ls[pos], l, mid, k);elsereturn query(rs[pos], mid + 1, r, k);
}void add(int pos, int pre, int l, int r, int k, int val){if (l == r){s[pos] = val;return ;}int mid = (l + r) >> 1;if (k <= mid){rs[pos] = rs[pre]; ls[pos] = getNew();add(ls[pos], ls[pre], l, mid, k, val);}else{ls[pos] = ls[pre]; rs[pos] = getNew();add(rs[pos], rs[pre], mid + 1, r, k, val);}a(pos);
}int main(){freopen("type.in", "r", stdin);freopen("type.out", "w", stdout);int q;q = read();rt[0] = 1, len[0] = 0;build(rt[0], 1, 100000);char op; int num; int rt_num = 0;for (int i = 1; i <= q; ++i){cin >> op;if (op == 'T'){char c; cin >> c;rt[++rt_num] = getNew();len[rt_num] = len[rt_num - 1] + 1;add(rt[rt_num], rt[rt_num - 1], 1, 100000, len[rt_num], (int)(c));}else if (op == 'Q'){num = read();printf("%c\n", (char)(query(rt[rt_num], 1, 100000, num)));}else if (op == 'U'){num = read(), ++rt_num;rt[rt_num] = rt[((rt_num - num - 1) > 0 ? (rt_num - num - 1) : 0)];ls[rt_num] = ls[((rt_num - num - 1) > 0 ? (rt_num - num - 1) : 0)], rs[rt_num] = rs[((rt_num - num - 1) > 0 ? (rt_num - num - 1) : 0)];len[rt_num] = len[rt_num - num - 1];}}fclose(stdin);fclose(stdout);return 0;
}
轉載于:https://www.cnblogs.com/linzhengmin/p/10925395.html
總結
以上是生活随笔為你收集整理的[洛谷1383]高级打字机 题解的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: CSS3——对齐 组合选择符 伪类
- 下一篇: jboss_log4j.xml配置