zoukankan      html  css  js  c++  java
  • 【算法#6】线段树

    如果我没记错的话应该是#6了。

    今天稍微搞懂了基础的线段树,但是因为其他的数据结构和算法都没有完全理解(无法处理穿衣服的题)所以说是咕掉了而不是get。

    首先搞一下线段树的结构。
    本质上就是一个按层次编号的二叉树,总共需要的空间大概在(2n)左右,注意别开小了。

    1~8
    1~4 5~8
    1~2 3~4 5~6 7~8
    1 2 3 4 | 5 6 7 8

    大概就是这个样子,第一层有(2^0)个节点,第i层有(2^{i-1})个节点。

    每个节点携带相对于该段的附加信息,(一般来说对于不同规模的数据,附加信息的规模应当相同否则就没有实用数据结构的意义了。)

    对于每个查询的区间,如果包含子右区间,那么递归进入子右区间,如果包含子左区间,递归进入子左区间并且改变查询区间的规模直到当前节点的范围完全契合查询区间。也就是,我们把原查询区间变成不超过log区间长度个(是这样吗?)的线段的并。很好理解对吧?我们上板子。

    int ql,qr;
    <modify> query(int o,int l,int r){
        int m=l+(r-l)/2,ans=<modify>;
        if(ql<=l&&r<=qr)
            return <res>[o];
        if(ql<=m)
            ans=<modify>(ans,query(o*2,l,m));
        if(qr>m)
            ans=<modify>(ans,query(o*2+1,m+1,r));
        return ans;
    }
    

    这个码风好诡异啊……这里是查询的,修改一下我把新码风的发来。

    int lb[maxn*2],rb[maxn*2];
    <modify> query(int o,int l,int r){
        int m=lb[o]+(rb[o]-lb[o])/2,ans=<modify>;
        if(lb[o]==l&&r==rb[o])
            return <res>[o];
        if(l<=m)
            ans=<modify>(ans,query(o*2,l,m));
        if(r>m)
            ans=<modify>(ans,query(o*2+1,m+1,r));
        return ans;
    }
    

    理论上没有问题?因为l和r都是可以预先处理好的。
    然后是update,单点修改。

    int p,v;
    void update(int o,int l,int r){
        int m=l+(r-l)/2;
        if(l==r)
            <res>[o]=v;
        else {
            if(p<=m)
                update(o*2,l,m);
            else update(o*2+1,m+1,r);
            <res>[o]=<modify>(<res>[o*2],<res>[o*2+1]);
        }
    }
    

    然后是构造过程,当然,对于每个点进行一次update操作也是可行的,只是复杂度上是nlogn,要是预先设置好每个叶节点的值再递归构造能够达到线性n的复杂度。

    int a[maxn];
    void build(int o,int l,int r){
        m=l+(r-l)/2;
        if(l==r)
            <res>[o]=a[o-maxn+1];
        else {
            build(o*2,l,m);
            build(o*2+1,m+1,r);
            <res>[o]=<modify>(<res>[o*2],<res>[o*2+1]);
        }
    }
    

    大概就是这样,点修改,更新,查询。学了后面的我再来补充。

  • 相关阅读:
    使用Boost::ptime构建高精度计时器
    static和extern
    通用js地址选择器
    js模拟抛出球运动
    前端用Webpact打包React后端Node+Express实现简单留言版
    webpack 打包一个简单react组件
    img及父元素(容器)实现类似css3中的background-size:contain / background-size:cover
    通用js函数集锦<来源于网络> 【二】
    通用js函数集锦<来源于网络/自己> 【一】
    向上滚动或者向下滚动分页异步加载数据(Ajax + lazyload)[上拉加载组件]
  • 原文地址:https://www.cnblogs.com/Schwarzkopf-Henkal/p/11840446.html
Copyright © 2011-2022 走看看