zoukankan      html  css  js  c++  java
  • HDU 3308 线段树求区间最长连续上升子序列长度

    题意:两种操作,Q L R查询L - R 的最长连续上升子序列长度,U pos val 单点修改值

    #include <bits/stdc++.h>
    #define N 100005
    using namespace std;
    int lcs[N<<2],pre[N<<2],suf[N<<2],arr[N];维护区间lcs长度,以左端点为起点的lcs长度,以右端点为终点的lcs长度,这么做是为了处理区间合并后区间总lcs值的更新
    void pushup(int l,int r,int rt)
    {
        int m=(l+r)>>1;
        lcs[rt]=max(lcs[rt<<1],lcs[rt<<1|1]);
        if(arr[m]<arr[m+1])lcs[rt]=max(lcs[rt],suf[rt<<1]+pre[rt<<1|1]);
        pre[rt]=pre[rt<<1];
        if(pre[rt<<1]==m-l+1&&arr[m]<arr[m+1])pre[rt]+=pre[rt<<1|1];
        suf[rt]=suf[rt<<1|1];
        if(suf[rt<<1|1]==r-m&&arr[m]<arr[m+1])suf[rt]+=suf[rt<<1];
    }
    void build(int l,int r,int rt)
    {
        if(l==r)
        {
            suf[rt]=pre[rt]=lcs[rt]=1;
            return;
        }
        int m=(l+r)>>1;
        build(l,m,rt<<1);
        build(m+1,r,rt<<1|1);
        pushup(l,r,rt);
    }
    void update(int pos,int val,int l,int r,int rt)
    {
        if(l==r)
        {
            arr[l]=val;
            return;
        }
        int m=(l+r)>>1;
        if(pos<=m)update(pos,val,l,m,rt<<1);
        if(pos>m)update(pos,val,m+1,r,rt<<1|1);
        pushup(l,r,rt);
    }
    int query(int L,int R,int l,int r,int rt)
    {
        if(L<=l&&r<=R)return lcs[rt];
        int m=(l+r)>>1;
        int mx=0;
        if(L<=m)mx=max(mx,query(L,R,l,m,rt<<1));
        if(m<R)mx=max(mx,query(L,R,m+1,r,rt<<1|1));//这时的mx只是各子区间的最大值,必须考虑子区间连接之后的状态
        int prex=min(R-m,pre[rt<<1|1]);
        int sufx=min(m-L+1,suf[rt<<1]);
        if(arr[m]<arr[m+1])mx=max(mx,prex+sufx);
        return mx;
    }
    int main()
    {
        int t,n,m;
        cin>>t;
        while(t--)
        {
            scanf("%d%d",&n,&m);
            for(int i=1;i<=n;i++)scanf("%d",arr+i);
            build(1,n,1);
            char cmd[10];
            int l,r;
            while (m--)
            {
                scanf("%s%d%d",cmd,&l,&r);
                if(cmd[0]=='U')update(l+1,r,1,n,1);
                else printf("%d\n",query(l+1,r+1,1,n,1));
            }
        }
        return 0;
    }
  • 相关阅读:
    Annotation
    injector
    Java容器(container)
    build tool(构建工具)maven和gradle安装方法
    version control(版本控制)
    函数式编程
    URI与URL
    超文本传输协议HTTP
    annotation的理解
    Injection
  • 原文地址:https://www.cnblogs.com/xusirui/p/9434488.html
Copyright © 2011-2022 走看看