hdu1698線段樹(區間更新)

2021-07-24 21:59:03 字數 1573 閱讀 7148

題目鏈結just a hook

乙個鎖鏈,其組成成部分有三種材料,金銀銅,分數為3、2、1,每次可以更換一段的材料,求最後的分數

鉤子最多長100,000

,操作最多有100,000次,肯定不能暴力-》線段樹

延遲標記lazy:

每個節點新增加乙個標記

lazy

,每次要更新節點時,不更新到葉節點,

記錄這個節點是否進行了某種修改(這種修改操作會影響其子節點。

假設要更新的區間為【1,4】,操作是給【1,4】區間裡面的每個值加上乙個值val

如圖,單點更新要一直更新到葉節點,醉話情況下,每次每個葉節點都要更新

加上lazy標價後,不用更新到葉節點,當當前節點的【l,r】包含在【a,b】中的時候,就更更新【l,r】的lazy標記

當查詢到【1,3】時,可以直接將【1,3】所記錄的值返回

當查詢到【1,2】時,就把lazy標價push_down到【1,2】和【3,3】(即其左右孩子),【1,3】的lazy清0

void push_down(int i)

}

**:

#include #include using namespace std;

const int maxn=100010;

int n;

struct node

segtree[maxn*3+5];

void push_up(int i)

void push_down(int i)

}void build(int i,int l,int r)

int mid=(l+r)/2;

build(i<<1,l,mid);

build((i<<1)|1,mid+1,r);

push_up(i);

}void update(int i,int l, int r, int val)

push_down(i);

int mid=(segtree[i].l+segtree[i].r)/2;

if(r<=mid)update(i<<1,l,r,val);

else if(midmid)return query((i<<1)|1,l,r);

else return query(i<<1,l,mid)+query((i<<1)|1,mid+1,r);

}int main()

printf("case %d: the total value of the hook is %d.\n",t,query(1,1,n));

}return 0;

}

HDU 1698 線段樹區間更新

之前一直覺得自己線段樹敲得很熟練,然後。某天。是的,就是我的資料結構周開始的時候我發現。我特麼才會單點更新是怎麼回事!只會區間查詢是腫麼回事!摔!恩。就是表達一下弱渣的心情。區間更新,用到延遲操作。延遲操作應該是這麼回事。線段樹的優越性就是體現在,第一是二分查詢,第二是區間操作。當我們需要多次對區間...

HDU 1698 線段樹(區間更新

題目鏈結 思路 今天才入門線段樹,一開始做這題還有一點懵,因為我開始的思路是區間更新時要考慮之前的狀態,比如之前的乙個需要更新的節點是鐵 1 現在再要求更新為鐵 1 則不進行更新.然後就要分很多情況去討論,很麻煩.所以另外想了乙個思路 受懶操作的啟發,我想我能不能定義乙個向下傳遞的值type 傳遞後...

hdu1698 線段樹更新區間

線段樹 更新整個區間 不要一直更新到節點,用乙個標記值 1標記是否雜色。更新的時候如果該段正好是要更新的段則將其更新即可。否則說明要更新的段與當前的tt step 這一段不一致,則要將tt step 這一段拆分成2段,遞迴呼叫更新step 2及step 2 1,更新後tt step 將變成雜色。所以...