[Persistent Segment Tree] Logu P3919

Logu P3919 [Template] Persistent Array (Persistent Segment Tree/Balanced Tree)

Topic:

Maintains an array of length N to support the following operations

  1. Modify a value at a location on a historical version

  2. Accessing values at a location on a historical version

In addition, a new version is generated for each operation (for operation 2, to generate an identical version without any changes).The version number is the number of the current operation (from the beginning, version 0 represents the initial state array)

Ideas:

  • A segment tree is built for logarithms.
  • Query operations are the same as segment tree operations.
  • When building and updating trees, be aware of the permanent marker of "persistence".Each update only needs to update the chain where the leaf nodes are located, and the rest inherits the information from the previous tree.

Insights:

  • This is really a template for a persistent segment tree that you tap yourself after you tap on the templates of the three Presidential Trees.After looking at the title, it is clear that the only difference between the Presidential Tree and the Presidential Tree is that the Presidential Tree (a persistent weighted segment tree) is a weighted segment tree, while the persistent segment tree is a normal segment tree.But I just didn't dare to hit it.Always feel something wrong.I also read blogs on the Internet without much interest and called a code on the internet, which is written differently from mine.I'm retrospectively updating my father's node.But his subfunction returns the update.(But I still like that little brother or sister's code style, and I have, like.Ha-ha) After a while, I found that there is no difference in fact, but the essence is the same.Just think, this is not the same as the chairman tree!!!!! Well, it took almost two hours on this topic, and the result is a lost board topic with the chairman tree.I cry
#include <iostream>
#include <cstdio>
#include <cmath>
#include <string>
#include <cstring>
#include <algorithm>
#include <limits>
#include <vector>
#include <stack>
#include <queue>
#include <set>
#include <map>
#define INF 0x3f3f3f3f
#define lowbit(x) x & (-x)

#define MID (l + r ) >> 1
#define lsn rt << 1
#define rsn rt << 1 | 1
#define Lson lsn, l, mid
#define Rson rsn, mid + 1, r
#define QL Lson, ql, qr
#define QR Rson, ql, qr
#define eps  1e-6

using namespace std;
typedef long long ll;
typedef unsigned long long ull;
const int maxN = 1e6 + 5;
int n, m, UP;
struct node{
    int ls, rs, val;
    node(int a = 0, int b = 0, int c = 0) : ls(a), rs(b), val(c) {}
}tree[maxN * 20];
int root[maxN], tot;
int arr[maxN];
void build_tree(int &now, int l, int r)
{
    now = ++ tot;
    if(l == r) { tree[now].val = arr[l]; return ; }
    int mid = MID;
    build_tree(tree[now].ls, l, mid);
    build_tree(tree[now].rs, mid + 1, r);
}
void update(int &now, int pre, int l, int r, int pos, int val)
{
    now = ++ tot;
    tree[now] = tree[pre];
    if(l == r) { tree[now].val = val; return; }
    int mid = MID;
    if(mid >= pos) update(tree[now].ls, tree[pre].ls, l, mid, pos, val);
    else update(tree[now].rs, tree[pre].rs, mid + 1, r, pos, val);
}
int query(int vers, int l, int r, int pos)
{
    if(l == r) { return tree[vers].val; }
    int mid = MID;
    if(mid >= pos) return query(tree[vers].ls, l, mid, pos);
    else return query(tree[vers].rs, mid + 1, r, pos);
}
int main()
{
    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; i <= m; i ++ )//After each operation is a new version
    {
        int version, op; scanf("%d%d", &version, &op);
        if(op == 1)//Modify Action
        {
            int pos, val; scanf("%d%d", &pos, &val);
            update(root[i], root[version], 1, n, pos, val);
        }
        else if(op == 2)//Query operation
        {
            int pos; scanf("%d", &pos);
            root[i] = root[version];//Currently a query operation, New Tree fully inherits the version tree
            printf("%d\n", query(root[version], 1, n, pos));
        }
    }
   return 0;
}

Two brushes

#include <iostream>
#include <cstdio>
#include <cmath>
#include <string>
#include <cstring>
#include <algorithm>
#include <limits>
#include <vector>
#include <stack>
#include <queue>
#include <set>
#include <map>
#define INF 0x3f3f3f3f
#define lowbit(x) x & (-x)

#define MID (l + r ) >> 1
#define lsn rt << 1
#define rsn rt << 1 | 1
#define Lson lsn, l, mid
#define Rson rsn, mid + 1, r
#define QL Lson, ql, qr
#define QR Rson, ql, qr
#define eps  1e-6

using namespace std;
typedef long long ll;
typedef unsigned long long ull;
const int maxN = 1e6 + 5;
int n, m, arr[maxN];
struct node{
    int ls, rs, val;
    node(int a = 0, int b = 0, int c = 0): ls(a), rs(b), val(c) {}
}tree[maxN * 20];
int root[maxN], tot;
void build_tree(int &rt, int l, int r)
{
    rt = tot ++;
    if(l == r) { tree[rt].val = arr[l]; return; }
    int mid = MID;
    build_tree(tree[rt].ls, l, mid);
    build_tree(tree[rt].rs, mid + 1, r);
}
void update(int &now, int pre, int l, int r, int pos, int val)
{
    now = ++ tot;
    tree[now] = tree[pre];
    if(l == r) { tree[now].val = val; return ; }
    int mid = MID;
    if(mid >= pos) update(tree[now].ls, tree[pre].ls, l, mid, pos, val);
    else update(tree[now].rs, tree[pre].rs, mid + 1, r, pos, val);
}
int query(int rt, int l, int r, int pos)
{
    if(l == r) return tree[rt].val;
    int mid = MID;
    if(mid >= pos) return query(tree[rt].ls, l, mid, pos);
    else return query(tree[rt].rs, mid + 1, r, pos);
}
int main()
{
    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; i <= m; i ++ )
    {
        int version, op, pos;
        scanf("%d%d%d", &version, &op, &pos);
        if(op == 1) // Modify Action
        {
            int val; scanf("%d", &val);
            update(root[i], root[version], 1, n, pos, val);
        }
        else
        {
            root[i] = root[version];
            printf("%d\n", query(root[version], 1, n, pos));
        }

    }
   return 0;
}

 

 

179 original articles were published. 53 were praised. 10,000 visits+
Private letter follow

Tags: REST

Posted on Tue, 14 Jan 2020 20:51:07 -0500 by gmann001