結果
| 問題 |
No.1441 MErGe
|
| コンテスト | |
| ユーザー |
|
| 提出日時 | 2021-03-26 22:26:47 |
| 言語 | C++14 (gcc 13.3.0 + boost 1.87.0) |
| 結果 |
TLE
(最新)
AC
(最初)
|
| 実行時間 | - |
| コード長 | 15,627 bytes |
| コンパイル時間 | 2,050 ms |
| コンパイル使用メモリ | 141,996 KB |
| 実行使用メモリ | 23,680 KB |
| 最終ジャッジ日時 | 2024-11-28 23:59:43 |
| 合計ジャッジ時間 | 19,373 ms |
|
ジャッジサーバーID (参考情報) |
judge3 / judge4 |
(要ログイン)
| ファイルパターン | 結果 |
|---|---|
| sample | AC * 2 |
| other | AC * 26 TLE * 2 |
ソースコード
#include <algorithm>
#include <bitset>
#include <cassert>
#include <cmath>
#include <complex>
#include <cstdio>
#include <deque>
#include <functional>
#include <iostream>
#include <map>
#include <numeric>
#include <queue>
#include <set>
#include <stack>
#include <string>
#include <unordered_map>
#include <unordered_set>
#include <vector>
#define REP(i, N) for (int i = 0; i < (int)N; i++)
#define FOR(i, a, b) for (int i = a; i < (int)b; i++)
#define ALL(x) (x).begin(), (x).end()
#pragma GCC optimize("Ofast")
#pragma GCC target("avx,avx2")
using namespace std;
constexpr int inf = 1 << 30;
constexpr long long llinf = 1LL << 62;
constexpr int mod = 1000000007; // 998244353;
constexpr int dy[4] = {-1, 0, 1, 0}, dx[4] = {0, -1, 0, 1};
using ll = long long;
using Pii = pair<int, int>;
using Pll = pair<ll, ll>;
inline int popcount(ll x) { return __builtin_popcountll(x); }
inline int div2num(ll x) { return __builtin_ctzll(x); }
inline bool bit(ll x, int b) { return (x >> b) & 1; }
template <class T>
bool chmax(T &a, const T &b) {
if (a < b) {
a = b;
return 1;
}
return 0;
}
template <class T>
bool chmin(T &a, const T &b) {
if (b < a) {
a = b;
return 1;
}
return 0;
}
template <class T>
string to_string(T s);
template <class S, class T>
string to_string(pair<S, T> p);
string to_string(char c) { return string(1, c); }
string to_string(string s) { return s; }
string to_string(const char s[]) { return string(s); }
template <class T>
string to_string(T v) {
if (v.empty()) return "{}";
string ret = "{";
for (auto x : v) ret += to_string(x) + ",";
ret.back() = '}';
return ret;
}
template <class S, class T>
string to_string(pair<S, T> p) {
return "{" + to_string(p.first) + ":" + to_string(p.second) + "}";
}
void debug() { cerr << endl; }
template <class Head, class... Tail>
void debug(Head head, Tail... tail) {
cerr << to_string(head) << " ";
debug(tail...);
}
template <class T>
vector<T> makev(int n, T v) {
return vector<T>(n, v);
}
struct IO {
#ifdef _WIN32
inline char getchar_unlocked() { return getchar(); }
inline void putchar_unlocked(char c) { putchar(c); }
#endif
std::string separator = " ";
template <class T>
inline void read(T &x) {
char c;
do {
c = getchar_unlocked();
} while (c != '-' && (c < '0' || '9' < c));
bool minus = 0;
if (c == '-') {
minus = 1;
c = getchar_unlocked();
}
x = 0;
while ('0' <= c && c <= '9') {
x *= 10;
x += c - '0';
c = getchar_unlocked();
}
if (minus) x = -x;
}
inline void read(std::string &x) {
char c;
do {
c = getchar_unlocked();
} while (c == ' ' || c == '\n');
x.clear();
do {
x += c;
c = getchar_unlocked();
} while (c != ' ' && c != '\n' && c != EOF);
}
template <class T>
inline void read(std::vector<T> &v) {
for (auto &x : v) read(x);
}
template <class S, class T>
inline void read(std::pair<S, T> &p) {
read(p.first);
read(p.second);
}
template <class Head, class... Tail>
inline void read(Head &head, Tail &...tail) {
read(head);
read(tail...);
}
template <class T>
inline void write(T x) {
char buf[32];
int p = 0;
if (x < 0) {
x = -x;
putchar_unlocked('-');
}
if (x == 0) putchar_unlocked('0');
while (x > 0) {
buf[p++] = (x % 10) + '0';
x /= 10;
}
while (p) {
putchar_unlocked(buf[--p]);
}
}
inline void write(std::string x) {
for (char c : x) putchar_unlocked(c);
}
inline void write(const char s[]) {
for (int i = 0; s[i] != 0; ++i) putchar_unlocked(s[i]);
}
template <class T>
inline void write(std::vector<T> v) {
if (v.empty()) return;
for (auto itr = v.begin(); itr + 1 != v.end(); ++itr) {
write(*itr);
write(separator);
}
write(v.back());
}
template <class Head, class... Tail>
inline void write(Head head, Tail... tail) {
write(head);
write(separator);
write(tail...);
}
template <class Head, class... Tail>
inline void writeln(Head head, Tail... tail) {
write(head, tail...);
write("\n");
}
void set_separator(std::string s) { separator = s; }
} io;
struct Prime {
int n;
vector<int> table;
vector<int> primes;
Prime(int _n = 100000) {
n = _n + 1;
table.resize(n, -1);
table[0] = 0;
table[1] = -1;
for (int i = 2; i * i < n; ++i) {
if (table[i] == -1) {
for (int j = i * i; j < n; j += i) {
table[j] = i;
}
}
}
}
void enumerate_primes() {
primes.clear();
for (int i = 2; i < n; ++i) {
if (table[i] == -1) primes.push_back(i);
}
}
vector<pair<long long, int>> prime_factor(long long x) {
map<long long, int> mp;
long long div = 2;
int p = 0;
while (n <= x && div * div <= x) {
if (x % div == 0) {
mp[div]++;
x /= div;
} else {
if (p + 1 < primes.size()) {
div = primes[++p];
} else {
div++;
}
}
}
if (x < n) {
while (table[x] != -1) {
mp[table[x]]++;
x /= table[x];
}
}
if (x > 1) mp[x]++;
vector<pair<long long, int>> ret;
for (auto p : mp) ret.push_back(p);
return ret;
}
};
template <int MOD = 1000000007>
struct Math {
vector<long long> fact, factinv, inv;
Math(int n = 100000) {
fact.resize(n + 1);
factinv.resize(n + 1);
inv.resize(n + 1);
fact[0] = fact[1] = 1;
factinv[0] = factinv[1] = 1;
inv[1] = 1;
for (int i = 2; i <= n; ++i) {
fact[i] = fact[i - 1] * i % MOD;
inv[i] = MOD - inv[MOD % i] * (MOD / i) % MOD;
factinv[i] = factinv[i - 1] * inv[i] % MOD;
}
}
long long C(int n, int r) {
if (n < r || n < 0 || r < 0) {
return 0;
} else {
return fact[n] * (factinv[r] * factinv[n - r] % MOD) % MOD;
}
}
long long P(int n, int r) {
if (n < r || n < 0 || r < 0) {
return 0;
} else {
return fact[n] * factinv[n - r] % MOD;
}
}
long long H(int n, int r) { return C(n + r - 1, r); }
};
struct UnionFind {
vector<int> data;
vector<vector<int>> groups;
UnionFind(int n) : data(n, -1) {}
int root(int v) { return data[v] < 0 ? v : data[v] = root(data[v]); }
bool unite(int u, int v) {
if ((u = root(u)) == (v = root(v))) {
return 1;
} else {
if (-data[u] < -data[v]) swap(u, v);
data[u] += data[v];
data[v] = u;
return 0;
}
}
int size(int v) { return -data[root(v)]; }
void make_groups() {
map<int, vector<int>> mp;
for (int i = 0; i < data.size(); ++i) mp[root(i)].push_back(i);
groups.clear();
for (auto p : mp) groups.push_back(p.second);
}
};
namespace phc {
long long modpow(long long a, long long n) {
long long res = 1;
while (n > 0) {
if (n & 1) res = res * a % mod;
a = a * a % mod;
n >>= 1;
}
return res;
}
long long modinv(long long a) {
long long b = mod, u = 1, v = 0;
while (b) {
long long t = a / b;
a -= t * b;
swap(a, b);
u -= t * v;
swap(u, v);
}
u %= mod;
if (u < 0) u += mod;
return u;
}
long long gcd(long long a, long long b) { return b != 0 ? gcd(b, a % b) : a; }
long long lcm(long long a, long long b) { return a / gcd(a, b) * b; }
} // namespace phc
template <int mod>
struct ModInt {
int x;
ModInt() : x(0) {}
ModInt(int64_t y) : x(y >= 0 ? y % mod : (mod - (-y) % mod) % mod) {}
ModInt &operator+=(const ModInt &p) {
if ((x += p.x) >= mod) x -= mod;
return *this;
}
ModInt &operator-=(const ModInt &p) {
if ((x += mod - p.x) >= mod) x -= mod;
return *this;
}
ModInt &operator*=(const ModInt &p) {
x = (int)(1LL * x * p.x % mod);
return *this;
}
ModInt &operator/=(const ModInt &p) {
*this *= p.inverse();
return *this;
}
ModInt operator-() const { return ModInt(-x); }
ModInt operator+(const ModInt &p) const { return ModInt(*this) += p; }
ModInt operator-(const ModInt &p) const { return ModInt(*this) -= p; }
ModInt operator*(const ModInt &p) const { return ModInt(*this) *= p; }
ModInt operator/(const ModInt &p) const { return ModInt(*this) /= p; }
ModInt inverse() const {
int a = x, b = mod, u = 1, v = 0, t;
while (b > 0) {
t = a / b;
swap(a -= t * b, b);
swap(u -= t * v, v);
}
return ModInt(u);
}
ModInt pow(int64_t n) const {
ModInt ret(1), mul(x);
while (n > 0) {
if (n & 1) ret *= mul;
mul *= mul;
n >>= 1;
}
return ret;
}
friend ostream &operator<<(ostream &os, const ModInt &p) { return os << p.x; }
friend istream &operator>>(istream &is, ModInt &a) {
int64_t t;
is >> t;
a = ModInt<mod>(t);
return (is);
}
static int get_mod() { return mod; }
};
template <class T>
struct RangeFold {
int n;
vector<T> dat;
using F = function<T(T, T)>;
const F f;
const T id;
RangeFold(int _n, const F _f, const T _id) : n(1), f(_f), id(_id) {
while (n < _n) n <<= 1;
dat.resize(2 * n, id);
}
void update(int i, T x) {
dat[i += n] = x;
while (i >>= 1) dat[i] = f(dat[i * 2], dat[i * 2 + 1]);
}
T query(int l, int r) {
T xl = id, xr = id;
for (l += n, r += n; l < r; l >>= 1, r >>= 1) {
if (l & 1) xl = f(xl, dat[l++]);
if (r & 1) xr = f(dat[--r], xr);
}
return f(xl, xr);
}
T &operator[](const int i) { return dat[n + i]; }
};
template <int L>
struct KthNext {
array<vector<int>, L> next;
KthNext(int n, function<int(int)> f) {
for (int i = 0; i < L; ++i) next[i].resize(n);
for (int i = 0; i < n; ++i) next[0][i] = f(i);
for (int i = 0; i < L - 1; ++i)
for (int j = 0; j < n; ++j) next[i + 1][j] = next[i][next[i][j]];
}
int get(int x, long long k) {
for (int i = 0; i < L; ++i)
if ((k >> i) & 1) x = next[i][x];
return x;
}
};
long long inv_count(vector<int> &vec) {
int n = vec.size();
vector<int> bit(n + 1);
long long ret = 0;
for (int i = n - 1; i >= 0; --i) {
int x = vec[i];
while (x > 0) {
ret += bit[x];
x -= x & -x;
}
x = vec[i] + 1;
while (x < n + 1) {
bit[x] += 1;
x += x & -x;
}
}
return ret;
}
using modint = ModInt<mod>;
template <class Monoid, class OperatorMonoid = Monoid>
struct RandomizedBinarySearchTree {
using F = function<Monoid(Monoid, Monoid)>;
using G = function<Monoid(Monoid, OperatorMonoid)>;
using H = function<OperatorMonoid(OperatorMonoid, OperatorMonoid)>;
using P = function<OperatorMonoid(OperatorMonoid, int)>;
inline int xor128() {
static int x = 123456789;
static int y = 362436069;
static int z = 521288629;
static int w = 88675123;
int t;
t = x ^ (x << 11);
x = y;
y = z;
z = w;
return w = (w ^ (w >> 19)) ^ (t ^ (t >> 8));
}
struct Node {
Node *l, *r;
int cnt;
Monoid key, sum;
OperatorMonoid lazy;
Node() = default;
Node(const Monoid &k, const OperatorMonoid &p)
: cnt(1), key(k), sum(k), lazy(p), l(nullptr), r(nullptr) {}
};
vector<Node> pool;
int ptr;
const Monoid M1;
const OperatorMonoid OM0;
const F f;
const G g;
const H h;
const P p;
RandomizedBinarySearchTree(int sz, const F &f, const Monoid &M1)
: pool(sz),
ptr(0),
f(f),
g(G()),
h(H()),
p(P()),
M1(M1),
OM0(OperatorMonoid()) {}
RandomizedBinarySearchTree(int sz, const F &f, const G &g, const H &h,
const P &p, const Monoid &M1,
const OperatorMonoid &OM0)
: pool(sz), ptr(0), f(f), g(g), h(h), p(p), M1(M1), OM0(OM0) {}
inline Node *alloc(const Monoid &key) {
return &(pool[ptr++] = Node(key, OM0));
}
virtual Node *clone(Node *t) { return t; }
inline int count(const Node *t) { return t ? t->cnt : 0; }
inline Monoid sum(const Node *t) { return t ? t->sum : M1; }
inline Node *update(Node *t) {
t->cnt = count(t->l) + count(t->r) + 1;
t->sum = f(f(sum(t->l), t->key), sum(t->r));
return t;
}
Node *propagate(Node *t) {
t = clone(t);
if (t->lazy != OM0) {
t->key = g(t->key, p(t->lazy, 1));
if (t->l) {
t->l = clone(t->l);
t->l->lazy = h(t->l->lazy, t->lazy);
t->l->sum = g(t->l->sum, p(t->lazy, count(t->l)));
}
if (t->r) {
t->r = clone(t->r);
t->r->lazy = h(t->r->lazy, t->lazy);
t->r->sum = g(t->r->sum, p(t->lazy, count(t->r)));
}
t->lazy = OM0;
}
return update(t);
}
Node *merge(Node *l, Node *r) {
if (!l || !r) return l ? l : r;
if (xor128() % (l->cnt + r->cnt) < l->cnt) {
l = propagate(l);
l->r = merge(l->r, r);
return update(l);
} else {
r = propagate(r);
r->l = merge(l, r->l);
return update(r);
}
}
pair<Node *, Node *> split(Node *t, int k) {
if (!t) return {t, t};
t = propagate(t);
if (k <= count(t->l)) {
auto s = split(t->l, k);
t->l = s.second;
return {s.first, update(t)};
} else {
auto s = split(t->r, k - count(t->l) - 1);
t->r = s.first;
return {update(t), s.second};
}
}
Node *build(int l, int r, const vector<Monoid> &v) {
if (l + 1 >= r) return alloc(v[l]);
return merge(build(l, (l + r) >> 1, v), build((l + r) >> 1, r, v));
}
Node *build(const vector<Monoid> &v) {
ptr = 0;
return build(0, (int)v.size(), v);
}
void dump(Node *r, typename vector<Monoid>::iterator &it) {
if (!r) return;
r = propagate(r);
dump(r->l, it);
*it = r->key;
dump(r->r, ++it);
}
vector<Monoid> dump(Node *r) {
vector<Monoid> v((size_t)count(r));
auto it = begin(v);
dump(r, it);
return v;
}
string to_string(Node *r) {
auto s = dump(r);
string ret;
for (int i = 0; i < s.size(); i++) ret += ", ";
return (ret);
}
void insert(Node *&t, int k, const Monoid &v) {
auto x = split(t, k);
t = merge(merge(x.first, alloc(v)), x.second);
}
void erase(Node *&t, int k) {
auto x = split(t, k);
t = merge(x.first, split(x.second, 1).second);
}
Monoid query(Node *&t, int a, int b) {
auto x = split(t, a);
auto y = split(x.second, b - a);
auto ret = sum(y.first);
t = merge(x.first, merge(y.first, y.second));
return ret;
}
void set_propagate(Node *&t, int a, int b, const OperatorMonoid &p) {
auto x = split(t, a);
auto y = split(x.second, b - a);
y.first->lazy = h(y.first->lazy, p);
t = merge(x.first, merge(propagate(y.first), y.second));
}
void set_element(Node *&t, int k, const Monoid &x) {
t = propagate(t);
if (k < count(t->l))
set_element(t->l, k, x);
else if (k == count(t->l))
t->key = t->sum = x;
else
set_element(t->r, k - count(t->l) - 1, x);
t = update(t);
}
int size(Node *t) { return count(t); }
bool empty(Node *t) { return !t; }
Node *makeset() { return nullptr; }
};
int main() {
int N, Q;
io.read(N, Q);
vector<ll> A(N);
io.read(A);
RandomizedBinarySearchTree<ll, ll> tree(
N + Q, [](ll l, ll r) { return l + r; }, 0LL);
auto root = tree.build(A);
REP(q, Q) {
int T, l, r;
io.read(T, l, r);
if (T == 1) {
ll sum = tree.query(root, l - 1, r);
auto lefts = tree.split(root, l - 1);
auto rights = tree.split(lefts.second, r - l + 1);
root = tree.merge(lefts.first, rights.second);
tree.insert(root, l - 1, sum);
} else {
cout << (tree.query(root, l - 1, r)) << "\n";
}
}
return 0;
}