線段樹二 (持續更新)

來源:互聯網
上載者:User

HDU 1689

http://acm.hdu.edu.cn/showproblem.php?pid=1698

這道題是使用懶操作的入門級的題目,線上段樹的結構體中,加一個flag標記該區間是否是同色的。當為同色,那麼在更新或者查詢的時候就可以偷懶了,有效降低時間複雜度。

//hdu 1698#include <iostream>#include <cstring>#include <cstdlib>#include <cstdio>#define MAX 100010#define lson l,m,k<<1#define rson m+1,r,k<<1|1using namespace std;typedef struct SEG{    int flag,v;}Seg;Seg seg[MAX<<2];void Init(int l,int r,int k){    seg[k].flag = 1;    seg[k].v = 1;    return ;}void PushDown(int k){    if(seg[k].flag)    {        seg[k<<1].flag=seg[k<<1|1].flag=1;        seg[k<<1].v=seg[k<<1|1].v=seg[k].v;        seg[k].flag=0;    }}void PushUp(int k){    if(seg[k<<1].flag&&seg[k<<1|1].flag)    {        if(seg[k<<1].v==seg[k<<1|1].v)        {            seg[k].flag=1;            seg[k].v=seg[k<<1].v;        }    }}void Update(int ll,int rr,int v,int l,int r,int k){    if(ll==l&&rr==r)    {        seg[k].flag=1;        seg[k].v=v;        return;    }    int m = (l+r)>>1;    PushDown(k);    if(rr<=m)        Update(ll,rr,v,lson);    else if(ll>m)        Update(ll,rr,v,rson);    else    {        Update(ll,m,v,lson);        Update(m+1,rr,v,rson);    }    PushUp(k);}int Query(int l,int r,int k){    if(seg[k].flag)    {        return seg[k].v*(r-l+1);    }    int m = (l+r)>>1;    return Query(lson)+Query(rson);}int main(){    int T;    int n,q;    int x,y,z;    scanf("%d",&T);    for(int cas=1;cas<=T;cas++)    {        scanf("%d%d",&n,&q);        Init(1,n,1);        while(q--)        {            scanf("%d%d%d",&x,&y,&z);            Update(x,y,z,1,n,1);        }        printf("Case %d: The total value of the hook is %d.\n",cas,Query(1,n,1));    }    return 0;}

HDU 3308 LCIS

http://acm.hdu.edu.cn/showproblem.php?pid=3308

這道題應該可以看成是一道區間合并的題目,在結構體中記錄左端點起始的最大上升序列長度,右端點結束的最大長度,以及整個區間的最大長度。為了在PushUp的時候方便,我們在記一個左右端點的值。更新很簡單,只要更新到葉子節點就行了。

只要在PushUp中注意一下就行了,具體見代碼。

#include <iostream>#include <cstring>#include <cstdlib>#include <cstdio>#define lson l,m,k<<1#define rson m+1,r,k<<1|1#define MAX 100100using namespace std;typedef struct SEG{    int lv,rv;    int lnum,mnum,rnum;}Seg;Seg seg[MAX<<2];void PushUp(int l,int r,int k){    int m = (l+r)>>1;    seg[k].lv=seg[k<<1].lv;    seg[k].rv=seg[k<<1|1].rv;    if((m-l+1)==seg[k<<1].lnum&&seg[k<<1].rv<seg[k<<1|1].lv)        seg[k].lnum=seg[k<<1].lnum+seg[k<<1|1].lnum;    else        seg[k].lnum=seg[k<<1].lnum;    if((r-m)==seg[k<<1|1].rnum&&seg[k<<1].rv<seg[k<<1|1].lv)        seg[k].rnum=seg[k<<1|1].rnum+seg[k<<1].rnum;    else        seg[k].rnum=seg[k<<1|1].rnum;    if(seg[k<<1].rv<seg[k<<1|1].lv)        seg[k].mnum=max(max(seg[k<<1].mnum,seg[k<<1|1].mnum),seg[k<<1].rnum+seg[k<<1|1].lnum);    else        seg[k].mnum=max(seg[k<<1].mnum,seg[k<<1|1].mnum);    seg[k].mnum=max(seg[k].mnum,max(seg[k].lnum,seg[k].rnum));}void Init(int l,int r,int k){    if(l==r)    {        scanf("%d",&seg[k].rv);        seg[k].lv=seg[k].rv;        seg[k].lnum=seg[k].mnum=seg[k].rnum=1;        return ;    }    int m = (l+r)>>1;    Init(lson);    Init(rson);    PushUp(l,r,k);}void Update(int id,int v,int l,int r,int k){    if(l==r)    {        seg[k].lv=seg[k].rv=v;        return ;    }    int m = (l+r)>>1;    if(id<=m)        Update(id,v,lson);    else        Update(id,v,rson);    PushUp(l,r,k);}Seg Query(int ll,int rr,int l,int r,int k){    if(ll==l&&rr==r)    {        return seg[k];    }    int m = (l+r)>>1;    if(rr<=m)        return Query(ll,rr,lson);    else if(ll>m)        return Query(ll,rr,rson);    else    {        Seg a = Query(ll,m,lson);        Seg b = Query(m+1,rr,rson);        Seg ans ;        ans.lv=a.lv,ans.rv=b.rv;        if(a.lnum==(m-ll+1)&&a.rv<b.lv)            ans.lnum=a.lnum+b.lnum;        else            ans.lnum=a.lnum;        if(b.rnum==(rr-m)&&a.rv<b.lv)            ans.rnum=b.rnum+a.rnum;        else            ans.rnum=b.rnum;        if(a.rv<b.lv)            ans.mnum=max(max(a.mnum,b.mnum),a.rnum+b.lnum);        else            ans.mnum=max(a.mnum,b.mnum);        ans.mnum=max(max(ans.lnum,ans.rnum),ans.mnum);        return ans;    }}int main(){    int T,n,m;    char op[4];    int a,b;    scanf("%d",&T);    while(T--)    {        scanf("%d%d",&n,&m);        Init(1,n,1);        while(m--)        {            scanf("%s%d%d",op,&a,&b);            ++a;            if(op[0]=='Q')            {                ++b;                Seg ans = Query(a,b,1,n,1);                printf("%d\n",ans.mnum);            }            else                Update(a,b,1,n,1);        }    }    return 0;}

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.