P3919 【模板】可持久化线段树 1(可持久化数组) - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)
#include <iostream>
#include <string>
#include <stack>
#include <vector>
#include <queue>
#include <deque>
#include <set>
#include <map>
#include <unordered_map>
#include <unordered_set>
#include <algorithm>
#include <cstdlib>
#include <cstdio>
#include <cstring>
#include <cmath>
#include <numeric>
#include <functional>
#include <climits>
//#include <windows.h>
using namespace std;
#define ll long long
#define db double
#define PII pair<int, int>
#define TUP tuple<int, int, int>
const int inf = 0x3f3f3f3f;
ll mod = 1e15 + 17;
ll q_pow(ll a, ll b) { ll ret = 1; while (b) { if (b & 1)ret = ret * a % mod; b >>= 1; a = a * a % mod; }return ret; }
ll gcd(ll a, ll b) { if (!b)return a; return gcd(b, a % b); }
const int N = 1e6 + 10;
int arr[N], n, m;
int root[N], lchild[N * 25], rchild[N * 25], val[N * 25], node_size = 0;
void build_tree(int& node, int l, int r) {
node = node_size++;
if (l == r) {
val[node] = arr[l];
return;
}
int mid = (l + r) >> 1;
build_tree(lchild[node], l, mid);
build_tree(rchild[node], mid + 1, r);
return;
}
void update(int& node, int pre_node, int l, int r, int ind, int v) {
node = node_size++;
lchild[node] = lchild[pre_node], rchild[node] = rchild[pre_node], val[node] = val[pre_node];
if (l == r) {
val[node] = v;
return;
}
int mid = (l + r) >> 1;
if (ind <= mid) update(lchild[node], lchild[pre_node], l, mid, ind, v);
else update(rchild[node], rchild[pre_node], mid + 1, r, ind, v);
return;
}
int query(int node, int l, int r, int ind) {
if (l == r) return val[node];
int mid = (l + r) >> 1;
if (ind <= mid) return query(lchild[node], l, mid, ind);
return query(rchild[node], mid + 1, r, ind);
}
void yelp_solve() {
scanf("%d %d", &n, &m);
for (int i = 1; i <= n; i++) scanf("%d", &arr[i]);
build_tree(root[0], 1, n);
for (int i = 1, pre, mode, ind, v; i <= m; i++) {
scanf("%d %d %d", &pre, &mode, &ind);
if (mode == 1) { // 修改
scanf("%d", &v);
update(root[i], root[pre], 1, n, ind, v);
} else { //查询
printf("%d\n", query(root[pre], 1, n, ind));
root[i] = root[pre];
}
}
return;
}
int main() {
int r = 1;
//cin >> r;
while (r--) {
yelp_solve();
}
return 0;
}