diff --git a/LibreOJ/106/106.cpp b/LibreOJ/106/106.cpp new file mode 100644 index 00000000..353caf3f --- /dev/null +++ b/LibreOJ/106/106.cpp @@ -0,0 +1,392 @@ +#include +#include + +using std::cin; +using std::cout; +const char endl = '\n'; + +const int N = 5e4 + 5; + +class Splay { + private: + struct node { + int value; + node *lchild, *rchild, *parent, **root; + size_t size, count; + + node() + : value(0), lchild(nullptr), rchild(nullptr), parent(nullptr), root(nullptr), size(0), count(0) {} + + node(const int &_value, node *_parent, node **_root) + : value(_value), lchild(nullptr), rchild(nullptr), parent(_parent), root(_root), size(1), count(1) {} + + ~node() { + if (lchild != nullptr) delete lchild; + if (rchild != nullptr) delete rchild; + } + + node *&child(unsigned int x) { + return !x ? lchild : rchild; + } + + unsigned relation() const { + return this == parent->lchild ? 0 : 1; + } + + size_t lsize() const { + return lchild == nullptr ? 0 : lchild->size; + } + + size_t rsize() const { + return rchild == nullptr ? 0 : rchild->size; + } + + void pushup() { + size = lsize() + count + rsize(); + } + + void rotate() { + node *old = parent; + unsigned x = relation(); + + if (old->parent != nullptr) { + old->parent->child(old->relation()) = this; + } + parent = old->parent; + + if (child(x ^ 1) != nullptr) { + child(x ^ 1)->parent = old; + } + old->child(x) = child(x ^ 1); + + child(x ^ 1) = old; + old->parent = this; + + old->pushup(); + pushup(); + } + + void splay(node *target = nullptr) { + while (parent != target) { + if (parent->parent == target) { + rotate(); + } else if (relation() == parent->relation()) { + parent->rotate(); + rotate(); + } else { + rotate(); + rotate(); + } + } + + if (target == nullptr) *root = this; + } + + node *predecessor() { + node *pred = lchild; + + while (pred->rchild != nullptr) { + pred = pred->rchild; + } + + return pred; + } + + node *successor() { + node *succ = rchild; + + while (succ->lchild != nullptr) { + succ = succ->lchild; + } + + return succ; + } + } * root; + + node *_insert(const int &value) { + node **target = &root, *parent = nullptr; + + while (*target != nullptr && (*target)->value != value) { + parent = *target; + parent->size++; + + if (value < parent->value) { + target = &parent->lchild; + } else { + target = &parent->rchild; + } + } + + if (*target == nullptr) { + *target = new node(value, parent, &root); + } else { + (*target)->count++; + (*target)->size++; + } + + (*target)->splay(); + + return root; + } + + node *find(const int &value) { + node *node = root; + + while (node != nullptr && value != node->value) { + if (value < node->value) { + node = node->lchild; + } else { + node = node->rchild; + } + } + + if (node != nullptr) { + node->splay(); + } + + return node; + } + + void erase(node *u) { + if (u == nullptr) return; + + if (u->count > 1) { + u->splay(); + u->count--; + u->size--; + + return; + } + + node *pred = u->predecessor(), + *succ = u->successor(); + + pred->splay(); + succ->splay(pred); + + delete succ->lchild; + succ->lchild = nullptr; + + succ->pushup(); + pred->pushup(); + } + + public: + Splay() + : root(nullptr) { + insert(std::numeric_limits::min()); + insert(std::numeric_limits::max()); + } + + ~Splay() { + delete root; + } + + void insert(const int &value) { + _insert(value); + } + + void erase(const int &value) { + erase(find(value)); + } + + unsigned rank(const int &value) { + node *node = find(value); + + if (node == nullptr) { + node = _insert(value); + int res = node->lsize(); + erase(node); + + return res; + } + + return node->lsize(); + } + + const int &predecessor(const int &value) { + node *node = find(value); + + if (node == nullptr) { + node = _insert(value); + const int &result = node->predecessor()->value; + erase(node); + return result; + } + + return node->predecessor()->value; + } + + const int &successor(const int &value) { + node *node = find(value); + + if (node == nullptr) { + node = _insert(value); + const int &result = node->successor()->value; + erase(node); + return result; + } + + return node->successor()->value; + } +}; + +struct node : Splay { + int l, r; + node *lchild, *rchild; + + node() + : l(0), r(0), lchild(nullptr), rchild(nullptr) {} + + node(const int &_l, const int &_r) + : l(_l), r(_r), lchild(nullptr), rchild(nullptr) {} + + ~node() { + if (lchild != nullptr) delete lchild; + if (rchild != nullptr) delete rchild; + } +} * root; + +int n, m, a[N]; + +void build(node *&u, int l, int r) { + u = new node(l, r); + + for (int i = l; i <= r; i++) { + u->insert(a[i]); + } + + if (l == r) return; + + int mid = (l + r) >> 1; + + build(u->lchild, l, mid); + build(u->rchild, mid + 1, r); +} + +int query_rank(node *u, int l, int r, int x) { + if (l <= u->l && u->r <= r) { + return u->rank(x) - 1; + } + + int mid = (u->l + u->r) >> 1; + int res = 0; + + if (l <= mid) res += query_rank(u->lchild, l, r, x); + if (r > mid) res += query_rank(u->rchild, l, r, x); + + return res; +} + +int query_kth(int _l, int _r, int k) { + int l = -1e8, r = 1e8, res = -1; + + while (l <= r) { + int mid = (l + r) >> 1; + + if (query_rank(root, _l, _r, mid) + 1 <= k) { + l = mid + 1; + res = mid; + } else { + r = mid - 1; + } + } + + return res; +} + +void modify(node *u, int p, int x) { + u->erase(a[p]); + u->insert(x); + + if (u->l == u->r) return; + + int mid = (u->l + u->r) >> 1; + + if (p <= mid) modify(u->lchild, p, x); + else modify(u->rchild, p, x); +} + +int query_pre(node *u, int l, int r, int x) { + if (l <= u->l && u->r <= r) { + return u->predecessor(x); + } + + int mid = (u->l + u->r) >> 1; + int res = std::numeric_limits::min(); + + if (l <= mid) res = std::max(res, query_pre(u->lchild, l, r, x)); + if (r > mid) res = std::max(res, query_pre(u->rchild, l, r, x)); + + return res; +} + +int query_suf(node *u, int l, int r, int x) { + if (l <= u->l && u->r <= r) { + return u->successor(x); + } + + int mid = (u->l + u->r) >> 1; + int res = std::numeric_limits::max(); + + if (l <= mid) res = std::min(res, query_suf(u->lchild, l, r, x)); + if (r > mid) res = std::min(res, query_suf(u->rchild, l, r, x)); + + return res; +} + +int main() { + std::ios::sync_with_stdio(false); + cin.tie(nullptr); + + cin >> n >> m; + + for (int i = 1; i <= n; i++) { + cin >> a[i]; + } + + build(root, 1, n); + + while (m--) { + int op; + + cin >> op; + + if (op == 1) { + int l, r, x; + + cin >> l >> r >> x; + + cout << query_rank(root, l, r, x) + 1 << endl; + } else if (op == 2) { + int l, r, k; + + cin >> l >> r >> k; + + cout << query_kth(l, r, k) << endl; + } else if (op == 3) { + int p, x; + + cin >> p >> x; + + modify(root, p, x); + a[p] = x; + } else if (op == 4) { + int l, r, x; + + cin >> l >> r >> x; + + cout << query_pre(root, l, r, x) << endl; + } else { // op == 5 + int l, r, x; + + cin >> l >> r >> x; + + cout << query_suf(root, l, r, x) << endl; + } + } + + delete root; + + return 0; +} diff --git a/LibreOJ/106/data/input0.in b/LibreOJ/106/data/input0.in new file mode 100644 index 00000000..644b3126 --- /dev/null +++ b/LibreOJ/106/data/input0.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:978d778808df00757dab64bc3f210eb847a9cadd5e03e1499b936715cb4d488f +size 384 diff --git a/LibreOJ/106/data/input0.out b/LibreOJ/106/data/input0.out new file mode 100644 index 00000000..12ffa6ec --- /dev/null +++ b/LibreOJ/106/data/input0.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:3fc690a2b7ec69fc1c9b7fb0011aa3504cfb5a587c121b7bbc7cc7a8ea687bfd +size 51 diff --git a/LibreOJ/106/data/input1.in b/LibreOJ/106/data/input1.in new file mode 100644 index 00000000..17efeb2a --- /dev/null +++ b/LibreOJ/106/data/input1.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:180082e9e720c7df6276a23493c4a5195d60b0bc45cec93af595aa78a510f9a0 +size 940 diff --git a/LibreOJ/106/data/input1.out b/LibreOJ/106/data/input1.out new file mode 100644 index 00000000..a380d94c --- /dev/null +++ b/LibreOJ/106/data/input1.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:5c3e64ea88c2199a623569e4c486969a05953d2afead9d19687dea70615bae68 +size 56 diff --git a/LibreOJ/106/data/input2.in b/LibreOJ/106/data/input2.in new file mode 100644 index 00000000..294faacd --- /dev/null +++ b/LibreOJ/106/data/input2.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:ae8cbba88bb86018314daee90fb1c70ffc29b43bbd42be14587177397e062a62 +size 2361 diff --git a/LibreOJ/106/data/input2.out b/LibreOJ/106/data/input2.out new file mode 100644 index 00000000..99033044 --- /dev/null +++ b/LibreOJ/106/data/input2.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:62f94373e7447731bd9596bf5b221291e2b2ed5164802f7c812927ee6b7ea7e1 +size 305 diff --git a/LibreOJ/106/data/input3.in b/LibreOJ/106/data/input3.in new file mode 100644 index 00000000..07350296 --- /dev/null +++ b/LibreOJ/106/data/input3.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:71ae206e1d23d1bbb8cd8c55c3dab4569478f3b663e41cffda78c94ea9be72ab +size 15991 diff --git a/LibreOJ/106/data/input3.out b/LibreOJ/106/data/input3.out new file mode 100644 index 00000000..a2af386f --- /dev/null +++ b/LibreOJ/106/data/input3.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:9fde53bd72016548d9b0e6a6dba143f8d77adc4568079fcaf4f7644832a16a3e +size 2671 diff --git a/LibreOJ/106/data/input4.in b/LibreOJ/106/data/input4.in new file mode 100644 index 00000000..df504c65 --- /dev/null +++ b/LibreOJ/106/data/input4.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:ad05364ddc249dc7e939acfc6199431e0e89ab68b00e4af3b5c98adf7228391f +size 50171 diff --git a/LibreOJ/106/data/input4.out b/LibreOJ/106/data/input4.out new file mode 100644 index 00000000..51770412 --- /dev/null +++ b/LibreOJ/106/data/input4.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:819876d5e4f3e7a7d07ccaf11419e7b1619a7ca8742f0a3f15a5080a45c999f6 +size 10851 diff --git a/LibreOJ/106/data/input5.in b/LibreOJ/106/data/input5.in new file mode 100644 index 00000000..3dbba572 --- /dev/null +++ b/LibreOJ/106/data/input5.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:b1d9806b1f763ecbf43635f7384f6ad49ac72bcdae26510f9ad6c5f55cef8100 +size 260570 diff --git a/LibreOJ/106/data/input5.out b/LibreOJ/106/data/input5.out new file mode 100644 index 00000000..81536b5d --- /dev/null +++ b/LibreOJ/106/data/input5.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:f4b5074fe037bb1707150ce994db418db2528778bce013b43aae77027d47c412 +size 55918 diff --git a/LibreOJ/106/data/input6.in b/LibreOJ/106/data/input6.in new file mode 100644 index 00000000..fb81dd88 --- /dev/null +++ b/LibreOJ/106/data/input6.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:addf40117357f5a2025bbeefd19c0fd6d8ceb526dc95e5b1b7feb01140238d3b +size 542388 diff --git a/LibreOJ/106/data/input6.out b/LibreOJ/106/data/input6.out new file mode 100644 index 00000000..1d7fd398 --- /dev/null +++ b/LibreOJ/106/data/input6.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:cef264f95e5be0abaca81da5a197003c96dee7cd9fe8d976f6023b60f6a267ee +size 114160 diff --git a/LibreOJ/106/data/input7.in b/LibreOJ/106/data/input7.in new file mode 100644 index 00000000..fba90434 --- /dev/null +++ b/LibreOJ/106/data/input7.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:c62df109da1a4556115b864c3eea71bea59ef4b5a152189042945df2eb77d927 +size 710611 diff --git a/LibreOJ/106/data/input7.out b/LibreOJ/106/data/input7.out new file mode 100644 index 00000000..49450c24 --- /dev/null +++ b/LibreOJ/106/data/input7.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:7ecf9f4df0c29bf8d5459b69a7275eacb9cebb424ff44fd20d1ecff1a6b4519c +size 115694 diff --git a/LibreOJ/106/data/input8.in b/LibreOJ/106/data/input8.in new file mode 100644 index 00000000..0814cfbb --- /dev/null +++ b/LibreOJ/106/data/input8.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:50016a760d70002b7349a4f9950dafda00d78ad3fef5df8883f7c81035a1c3e2 +size 1388140 diff --git a/LibreOJ/106/data/input8.out b/LibreOJ/106/data/input8.out new file mode 100644 index 00000000..b4b39438 --- /dev/null +++ b/LibreOJ/106/data/input8.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:e23fb287a9206c151823f632128b549814c38c6e2478a486e402aa6b80798cc2 +size 289639 diff --git a/LibreOJ/106/data/input9.in b/LibreOJ/106/data/input9.in new file mode 100644 index 00000000..bc1c4124 --- /dev/null +++ b/LibreOJ/106/data/input9.in @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:1f6db823d225b93c576b94bccf93b89f1ecc6121d082cd6c0739ede09f2e66ec +size 1389265 diff --git a/LibreOJ/106/data/input9.out b/LibreOJ/106/data/input9.out new file mode 100644 index 00000000..952a7820 --- /dev/null +++ b/LibreOJ/106/data/input9.out @@ -0,0 +1,3 @@ +version https://git-lfs.github.com/spec/v1 +oid sha256:86d5d788c2cfa749216de8e30c81013356d3dcf46dff73b5ff95627822b8e2dd +size 290199