zoukankan      html  css  js  c++  java
  • 线段树学习

    标记下模板,需要的时候抄写

    1.线段树 单点更新,区间查询

    https://hihocoder.com/contest/offers27/problem/3

     1 #include<bits/stdc++.h>
     2 #define pb push_back
     3 typedef long long ll;
     4 using namespace std;
     5 typedef pair<int, int> pii;
     6 const int maxn = 2e5 + 10;
     7 int f[maxn * 4];
     8 int a[maxn];
     9 vector<int> e[100010];
    10 int n;
    11 int ti[maxn];
    12 int cnt = 0;
    13 int rt[100010][2];
    14 void dfs(int u, int p) {
    15     ti[++cnt] = u;
    16     rt[u][0] = cnt;
    17     for (int  x : e[u]) {
    18         if(x == p) continue;
    19         dfs(x, u);
    20     }
    21     ti[++cnt] = u;
    22     rt[u][1] = cnt;
    23 }
    24 void bt(int x, int y, int o) {
    25     if(x == y) {
    26         f[o] = a[ti[x]];
    27         return;
    28     }
    29     int mid = (x + y) >> 1;
    30     bt(x, mid, o * 2);
    31     bt(mid + 1, y, o * 2 + 1);
    32     f[o] = min(f[o * 2], f[o * 2 + 1]);
    33 }
    34 int tx1, ty1;
    35 int ask(int x, int y, int o) {
    36     if(x >= tx1 && y <= ty1) return f[o];
    37     int mid = (x + y) >> 1;
    38     int res = INT_MAX;
    39     if(tx1 <= mid)
    40         res = min(res, ask(x, mid, o * 2));
    41     if(ty1 >= mid + 1)
    42         res = min(res, ask(mid + 1, y, o * 2 + 1));
    43     return res;
    44 }
    45 void up(int x, int y, int o) {
    46     if(y < tx1 || x > tx1) return;
    47     if(x == y && x == tx1) {
    48         f[o] = ty1;
    49         //cout << o << " asd " << f[o] << " " << y1 << endl;
    50         return;
    51     }
    52     int mid = (x + y) >> 1;
    53     if(tx1 <= mid) up(x, mid, o * 2);
    54     else up(mid + 1, y, o * 2 + 1);
    55     f[o] = min(f[o * 2], f[o * 2 + 1]);
    56     //cout << o << " asd " << f[o] << endl;
    57 }
    58 void solve() {
    59     scanf("%d", &n);
    60     for (int i = 1; i <= n; i++) scanf("%d", &a[i]);
    61     int x, y;
    62     for (int i = 2; i <= n; i++) {
    63         scanf("%d", &x);
    64         e[x].pb(i);
    65     }
    66     dfs(1, 0);
    67     bt(1, cnt, 1);
    68     int m;
    69     scanf("%d", &m);
    70     while(m--) {
    71         scanf("%d%d", &x, &y);
    72         //cout << x << " " << y << endl;
    73         if(x == 1) {
    74             scanf("%d", &x);
    75             swap(x, y);
    76             tx1 = rt[x][0];
    77             ty1 = y;
    78             up(1, cnt, 1);
    79             tx1 = rt[x][1];
    80             up(1, cnt, 1);
    81 
    82         } else {
    83             tx1 = rt[y][0]; ty1 = rt[y][1];
    84             int t = ask(1, cnt, 1);
    85             printf("%d
    ", t);
    86         }
    87     }
    88 
    89 }
    90 
    91 int main() {
    92     //freopen("test.in", "r", stdin);
    93     //freopen("test.out", "w", stdout);
    94     solve();
    95     return 0;
    96 }
    View Code

    2. 区间更新,区间查询, lazy标记

    https://hihocoder.com/contest/offers28/problem/3

     1 #include<bits/stdc++.h>
     2 #define pb push_back
     3 typedef long long ll;
     4 using namespace std;
     5 typedef pair<int, int> pii;
     6 const int maxn = 1e5 + 10;
     7 
     8 int n, m, q;
     9 pii a[maxn], b[maxn];
    10 
    11 //tree
    12 int x, y, v;
    13 int sum[1863000],tag[1863000];
    14 #define pd(o,l,r) tag[o<<1] += tag[o], tag[o<<1|1]+=tag[o],sum[o<<1]+=tag[o],sum[o<<1|1]+=tag[o],tag[o]=0
    15 #define mid (l+r>>1)
    16 void update(int o,int l,int r){
    17     //cout << o << " " << l << " " << r << endl;
    18     x<=l&&r<=y?
    19     tag[o]+=v,sum[o]=sum[o] + v:
    20         (tag[o]?pd(o,l,r),1:1,x<=mid?update(o<<1,l,mid),1:1,mid<y?update(o<<1|1,mid+1,r),1:1,sum[o]= max(sum[o<<1], sum[o<<1|1]));
    21 }int query(int o,int l,int r){
    22     int t = 0;
    23     x<=l&&r<=y?t =  sum[o]:(tag[o]?pd(o,l,r),1:1,
    24     x<=mid?t = max(t, query(o<<1,l,mid)),1:1,mid<y?t = max(t, query(o<<1|1,mid+1,r)),1:1);
    25     return t;
    26 }
    27 void solve() {
    28     scanf("%d%d", &n, &m);
    29     int tx, ty;
    30     set<int> se;
    31     map<int, int> ma;
    32     for (int i = 0; i < n; i++) {
    33         scanf("%d%d", &tx, &ty);
    34         a[i] = {tx, ty}; se.insert(tx); se.insert(ty);
    35     }
    36     scanf("%d", &q);
    37     for (int i = 0; i < q; i++) {
    38         scanf("%d%d", &tx, &ty);
    39         b[i] = {tx, ty}; se.insert(tx); se.insert(ty);
    40     }
    41     int cnt = 0;
    42     for (int t : se) {
    43         ma[t] = ++cnt;
    44     }
    45     for (int i = 0; i < n; i++) {
    46         x = ma[a[i].first], y = ma[a[i].second]-1;
    47         //cout << x << " " << y << endl;
    48         v = 1;
    49 
    50         update(1, 1, cnt);//cout << "asd" << endl;
    51     }
    52     for (int i = 0; i < q; i++) {
    53         x = ma[b[i].first], y = ma[b[i].second]-1;
    54         //cout << x << " " << y << endl;
    55         int t = query(1, 1, cnt) + 1;
    56         if(t > m) puts("NO");
    57         else puts("YES");
    58     }
    59 }
    60 
    61 int main() {
    62     //freopen("test.in", "r", stdin);
    63     //freopen("test.out", "w", stdout);
    64     solve();
    65     return 0;
    66 }
    View Code

    https://hihocoder.com/contest/hiho20/problem/1

     1 #include<cstdio>
     2 #define mid (l+r>>1)
     3 #define pd(o,l,r) tag[o<<1]=tag[o<<1|1]=tag[o],sum[o<<1]=tag[o]*(mid-l+1),sum[o<<1|1]=tag[o]*(r-mid),tag[o]=0
     4 int ans,sum[263000],tag[263000],v,n,q,op,x,y,i,aa;char ch;int F(){
     5     while(ch=getchar(),ch<'0'||ch>'9');aa=ch-48;
     6     while(ch=getchar(),ch>='0'&&ch<='9')aa=aa*10+ch-48;return aa;
     7 }void bt(int o,int l,int r){
     8     l==r?sum[o]=F():(bt(o<<1,l,mid),bt(o<<1|1,mid+1,r),sum[o]=sum[o<<1]+sum[o<<1|1]);
     9 }void update(int o,int l,int r){
    10     x<=l&&r<=y?tag[o]=v,sum[o]=v*(r-l+1):(tag[o]?pd(o,l,r),1:1,
    11     x<=mid?update(o<<1,l,mid),1:1,mid<y?update(o<<1|1,mid+1,r),1:1,sum[o]=sum[o<<1]+sum[o<<1|1]);
    12 }void query(int o,int l,int r){
    13     x<=l&&r<=y?ans+=sum[o]:(tag[o]?pd(o,l,r),1:1,
    14     x<=mid?query(o<<1,l,mid),1:1,mid<y?query(o<<1|1,mid+1,r),1:1);
    15 }int main(){
    16     for(bt(1,1,n=F()),q=F();q--;op=F(),x=F(),y=F(),
    17     op?v=F(),update(1,1,n),1:(ans=0,query(1,1,n),printf("%d
    ",ans)));
    18 }
    View Code

    上面这个代码是十佳代码代码里面的,我一般都是学的这个模板。

  • 相关阅读:
    数据库基本操作
    常用开发工具的一些问题
    jquery 之ajax获取数据
    处理动态添加的元素事件无效
    javascript面向对象
    项目中使用rem的方法
    vue实时获取路由地址
    echarts修改线条颜色的方法
    顶部导航栏点击数据不缓存
    sass-loader版本报错问题(Error: Callback was already called)
  • 原文地址:https://www.cnblogs.com/y119777/p/7599228.html
Copyright © 2011-2022 走看看