青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

隨筆 - 97, 文章 - 22, 評論 - 81, 引用 - 0
數據加載中……

HDU 3308 LCIS

題目鏈接:http://acm.hdu.edu.cn/showproblem.php?pid=3308

/*
題意:
    給出一個長度為N(N <= 100000)的數列,然后是兩種操作:
U A B: 將第A個數替換為B (下標從零開始)
Q A B: 輸出區間[A, B]的最長連續遞增子序列
注意:操作的數目m <= 100000。

解法:
線段樹

思路:
    做慣了區間最值、求和、修改、染色的等問題,這題算比較新穎
的了,由這題可以看出線段樹的一般解法,因為這題要求保存的信息
比較多,每個線段樹的結點要求保存的信息有以下幾個:

    int lMax;       // 包含結點左端點的最長連續遞增子序列的長度
    int rMax;       // 包含結點右端點的最長連續遞增子序列的長度
    int Max;        // 當前結點的最長連續遞增子序列的長度
    int lVal, rVal; // 當前結點管轄的區間左右端點的數值
    int l, r;       // 當前結點管轄的區間

我們用以下函數從左右兒子中得到當前結點的信息:
void UpdateBy(Tree* ls, Tree* rs);
之所以把它寫成函數是因為這里的處理比較麻煩,很容易出錯,并且需要
調用多次,這個函數的作用就是通過左右兒子的信息填充本身的信息。

lVal、rVal、l、r等信息比較容易求得。
lMax和rMax的值就比較麻煩了,需要分情況討論(下面的len表示區間長度):
1. 左兒子最右邊的值 < 右兒子最左邊的值

    lMax = (左兒子的lMax == 左兒子的len) ? 左兒子的len + 右兒子的lMax : 左兒子的lMax;
    rMax = (右兒子的rMax == 右兒子的len) ? 右兒子的len + 左兒子的rMax : 右兒子的rMax;
    Max  = MAX(左兒子的rMax + 右兒子的lMax, 左兒子的Max, 右兒子的Max, lMax, rMax);

2. 左兒子最右邊的值 >= 右兒子最左邊的值

    lMax = 左兒子的lMax;
    rMax = 右兒子的rMax;
    Max  = MAX(左兒子的Max, 右兒子的Max);

一開始讀入的時候有一連串數字,需要建樹,建樹的時候每次回歸時需要
將兒子的信息傳遞給父親,調用UpdateBy(Tree* ls, Tree* rs)函數,每
次插入完畢后回歸時,信息會更新,也需要調用。詢問時,返回的也是一
個線段樹結點,并且需要將答案合并,還是需要調用UpdateBy函數,所以
總的來說需要調用三次,把它寫成一個函數還是勢在必行的。
*/



#include 
<iostream>

using namespace std;

#define maxn 100010

struct Tree {
    
int lMax;       // 包含結點左端點的最長連續遞增子序列
    int rMax;       // 包含結點右端點的最長連續遞增子序列
    int Max;        // 當前結點的最長連續遞增子序列
    int lVal, rVal; // 當前區間左右端點的值
    int l, r;       // 當前結點管轄的區間
    int son[2];

    
void clear() {
        son[
0= son[1= -1;
    }

    
void UpdateBy(Tree* ls, Tree* rs);
    
void Unit(int nl, int nr, int nv);
    
int len() {
        
return r - l + 1;
    }

}
T[maxn*4];
int root, tot;
int val[ maxn ];

int MAX(int a, int b) {
    
return a > b ? a : b;
}


int MAX(int a, int b, int c) {
    
return MAX(MAX(a, b), c);
}


int MAX(int a, int b, int c, int d) {
    
return MAX( MAX(a, b), MAX(c, d) );
}


void Tree::UpdateBy(Tree* ls, Tree* rs) {
    lVal 
= ls->lVal;
    rVal 
= rs->rVal;
    l    
= ls->l;
    r    
= rs->r;
    
if(ls->rVal < rs->lVal) {
        lMax 
= (ls->lMax == ls->len()) ? ls->len() + rs->lMax : ls->lMax;
        rMax 
= (rs->rMax == rs->len()) ? rs->len() + ls->rMax : rs->rMax;
        
        Max  
= MAX(ls->rMax + rs->lMax, ls->Max, rs->Max);
        Max  
= MAX(Max, lMax, rMax);

    }
else {
        lMax 
= ls->lMax;
        rMax 
= rs->rMax;
        Max  
= MAX(ls->Max, rs->Max);
    }

}


void Tree::Unit(int nl, int nr, int nv) {
    lMax 
= rMax = 1; Max = 1;
    lVal 
= rVal = nv;
    l 
= nl; r = nr;
}


int GetID(int& root) {
    
if(root == -1{
        root 
= tot++;
        T[root].clear();
    }

    
return root;
}


void Build(int& root, int l, int r) {
    GetID(root);
    
if(l == r) {
        T[root].Unit(l, r, val[l]);
        
return ;
    }

    
int mid = (l + r) >> 1;
    Build(T[root].son[
0], l, mid);
    Build(T[root].son[
1], mid+1, r);

    T[root].UpdateBy(
&T[ T[root].son[0] ], &T[ T[root].son[1] ]);
}


void Insert(int root, int nPos, int val) {
    
if(nPos < T[root].l || nPos > T[root].r)
        
return ;
    
if(T[root].l == nPos && nPos == T[root].r) {
        T[root].Unit(nPos, nPos, val);
        
return ;
    }

    Insert(T[root].son[
0], nPos, val);
    Insert(T[root].son[
1], nPos, val);

    T[root].UpdateBy(
&T[ T[root].son[0] ], &T[ T[root].son[1] ]);
}


Tree Query(
int root, int nl, int nr) {
    
if(nl > T[root].r || nr < T[root].l) {
        Tree tmp;
        tmp.Max 
= -1;
        
return tmp;
    }


    
if(nl <= T[root].l && T[root].r <= nr) {
        
return T[root];
    }

    Tree A, B;
    A 
= Query(T[root].son[0], nl, nr);
    B 
= Query(T[root].son[1], nl, nr);
    
if(A.Max == -1)
        
return B;
    
else if(B.Max == -1)
        
return A;
    
else {
        Tree X;
        X.UpdateBy(
&A, &B);
        
return X;
    }

}


int n, m;
int main() {
    
int t, i;
    scanf(
"%d"&t);

    
while(t--{
        scanf(
"%d %d"&n, &m);
        
for(i = 1; i <= n; i++{
            scanf(
"%d"&val[i]);
        }

        tot 
= 0;
        root 
= -1;
        Build(root, 
1, n);
        
while(m--{
            
char str[10];
            
int A, B;
            scanf(
"%s %d %d", str, &A, &B);
            
if(!strcmp(str, "U")) {
                Insert(root, A
+1, B);
            }
else {
                Tree tmp 
= Query(root, A+1, B+1);
                printf(
"%d\n", tmp.Max);
            }

        }

    }

    
return 0;
}

posted on 2011-04-01 02:36 英雄哪里出來 閱讀(2044) 評論(2)  編輯 收藏 引用 所屬分類: 線段樹

評論

# re: HDU 3308 LCIS  回復  更多評論   

受教了!狂膜拜!
2011-08-15 10:36 | Now_I

# re: HDU 3308 LCIS  回復  更多評論   

新生,敢問,為什么這樣區分是對的呢??
還是沒有想明白,請大神解析一下。
1. 左兒子最右邊的值 < 右兒子最左邊的值

lMax = (左兒子的lMax == 左兒子的len) ? 左兒子的len + 右兒子的lMax : 左兒子的lMax;
rMax = (右兒子的rMax == 右兒子的len) ? 右兒子的len + 左兒子的rMax : 右兒子的rMax;
Max = MAX(左兒子的rMax + 右兒子的lMax, 左兒子的Max, 右兒子的Max, lMax, rMax);

謝謝了。
2013-04-27 18:57 | ni hao
青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            久久99伊人| 久久国产精品黑丝| 亚洲高清毛片| 亚洲一区二区成人| 日韩一级在线观看| 久久久之久亚州精品露出| 午夜日韩在线| 国产精品高潮久久| 日韩视频免费观看高清在线视频 | 欧美日韩xxxxx| 鲁鲁狠狠狠7777一区二区| 国产精品私房写真福利视频| 亚洲精品在线一区二区| 91久久线看在观草草青青| 久久精品主播| 久久久噜噜噜久久| 国产午夜精品美女视频明星a级| 一本久久综合亚洲鲁鲁| 亚洲无亚洲人成网站77777| 欧美激情在线观看| 亚洲精品欧美| 在线亚洲精品| 欧美偷拍另类| 一区二区免费看| 亚洲尤物精选| 国产精品日韩一区| 午夜亚洲性色福利视频| 久久国产精品72免费观看| 国产一区二区三区电影在线观看| 香蕉av777xxx色综合一区| 欧美一级在线播放| 国产一区二区三区久久久| 午夜精品成人在线| 久久婷婷麻豆| 91久久精品国产91久久性色| 你懂的亚洲视频| 最近中文字幕日韩精品| 夜夜爽夜夜爽精品视频| 欧美丝袜一区二区三区| 亚洲综合第一| 巨乳诱惑日韩免费av| 91久久久久| 欧美日韩一区国产| 亚洲欧美成人| 美女视频黄免费的久久| 亚洲精品国产精品乱码不99| 欧美视频二区36p| 香蕉成人久久| 欧美激情一区二区三区高清视频| 一本到高清视频免费精品| 国产精品人人爽人人做我的可爱| 小黄鸭精品密入口导航| 欧美激情五月| 亚洲欧美综合网| 亚洲国产精品高清久久久| 欧美日韩国产免费观看| 午夜在线视频一区二区区别| 欧美电影在线播放| 亚洲免费视频一区二区| 激情久久久久久| 欧美日本韩国一区| 欧美一级视频精品观看| 亚洲国产精品va在线看黑人| 欧美一级二级三级蜜桃| 亚洲人成毛片在线播放女女| 国产精品欧美在线| 欧美11—12娇小xxxx| 亚洲欧美日韩精品久久| 亚洲人成小说网站色在线| 久久视频在线看| 亚洲一区欧美| 亚洲全黄一级网站| 国外视频精品毛片| 国产精品国产三级国产普通话蜜臀| 欧美中文在线视频| 亚洲一二三区在线观看| 91久久夜色精品国产九色| 久久亚洲一区二区三区四区| 亚洲一区二区久久| 亚洲日韩欧美视频一区| 在线观看日韩国产| 国产精品夜夜夜| 欧美三级黄美女| 免费视频一区| 久久久www成人免费无遮挡大片| 亚洲少妇自拍| 亚洲精品在线视频观看| 亚洲成人中文| 欧美99久久| 美女被久久久| 久久久久免费观看| 欧美在线一级视频| 亚洲欧美视频一区二区三区| 亚洲视频综合在线| 妖精视频成人观看www| 亚洲精品日韩在线| 91久久国产综合久久91精品网站| 国产综合色精品一区二区三区| 国产精品久久久久999| 欧美日韩蜜桃| 欧美日韩精品一本二本三本| 欧美成人在线网站| 欧美大片国产精品| 欧美激情精品久久久久久| 免费在线亚洲欧美| 欧美成人综合| 欧美精品日韩综合在线| 欧美日本中文| 欧美日韩中文| 国产精品推荐精品| 国产人成精品一区二区三| 国产欧美欧美| 国内综合精品午夜久久资源| 黄色亚洲精品| 亚洲黄色天堂| 夜夜嗨av一区二区三区四区| 一区二区欧美精品| 亚洲男人av电影| 欧美一区二区三区啪啪| 久久久久国产一区二区三区四区| 久久精品理论片| 免播放器亚洲一区| 亚洲国产精品嫩草影院| 亚洲久久成人| 亚洲欧美在线一区| 久久躁日日躁aaaaxxxx| 欧美成人精品一区| 国产精品成人av性教育| 国产伦精品一区二区三区在线观看 | 国产一区二区三区在线观看视频 | 亚洲高清视频在线| 日韩一级片网址| 亚洲欧美国产制服动漫| 久久精品国产视频| 欧美成人四级电影| 日韩视频一区| 午夜精品在线观看| 免费成人高清视频| 国产精品老牛| 亚洲第一偷拍| 在线视频亚洲| 久久综合九色综合欧美狠狠| 亚洲国产另类久久精品| 亚洲一区二区在线视频 | 欧美日韩中文字幕精品| 国产午夜亚洲精品不卡| 亚洲人人精品| 久久狠狠亚洲综合| 亚洲欧洲精品成人久久奇米网 | 午夜精品久久久久久久99黑人 | 久久亚洲综合| 国产精品久久久久久亚洲调教| 伊人狠狠色丁香综合尤物| 一本色道久久综合狠狠躁篇的优点 | 亚洲一区二区视频在线| 久久综合狠狠| 国产九区一区在线| 99在线精品观看| 免费精品99久久国产综合精品| 一区二区高清视频在线观看| 久久亚洲精品网站| 国产日韩欧美中文| 一区二区不卡在线视频 午夜欧美不卡在 | 噜噜噜91成人网| 一本色道久久精品| 欧美成人免费播放| 激情综合视频| 欧美一级大片在线免费观看| 亚洲激情成人| 老鸭窝91久久精品色噜噜导演| 国产伦精品一区| 中日韩视频在线观看| 久久激情视频久久| 久久精品99无色码中文字幕| 欧美日韩精品免费观看视频完整| 一区二区三区在线观看欧美| 午夜精品久久99蜜桃的功能介绍| 亚洲靠逼com| 欧美成年视频| 亚洲国产一区二区三区在线播| 欧美中文字幕在线视频| 一区二区三区日韩在线观看 | 久久在线免费观看视频| 国产一区二区三区免费不卡| 亚洲欧美区自拍先锋| 亚洲免费av网站| 欧美女激情福利| 日韩视频在线一区二区三区| 欧美激情五月| 欧美成人a视频| 亚洲精品久久久久久久久久久久久 | 欧美成人第一页| 久久久久久综合| 亚洲成色www8888| 欧美 日韩 国产在线| 久久裸体视频| 亚洲国产精品va| 亚洲黄色小视频| 欧美日韩亚洲综合| 亚洲欧美日韩视频一区|