線段樹GO實現

2021-10-22 18:41:16 字數 1303 閱讀 7733

var sum int

var lazytint

var arrint

//改變了區間中某乙個值或某些值時,我們需要沿著線段樹向上更新改變值的節點與根節點間的所有值,可以看出這部操作與線段樹的高度有關,複雜度為o(logn)

func pushup(idx int)

//build

func build(left,right,idx int)

var mid=left+(right-left)/2

build(left,mid,idx*2)

build(mid+1,right,idx*2+1)

pushup(idx)

}//單點修改。改變區件中的某乙個值,即在樹中找到對應的葉節點,更新其值,然後遞迴改變該節點到根節點路徑上所有節點的值

func updatepoint(changedidx,changedvalue,left,right,idx int)

var mid=left+(right-left)/2

if changedidx<=midelse

pushup(idx)//子節點更新了,所以本節點也需要更新資訊

}//區間修改,在區間修改的時候我們引入乙個新的概念——懶惰標記

////懶惰標記:表示本節點的統計資訊已經根據標記更新過了,但是本節點的子節點還沒有更新

//func pushdown(idx,leftnum,righttree int)

}func updateseg(changedleftidx,changedrightidx, changedvalue, left, right,idx int)

var mid=left+(right-left)/2

pushdown(idx,mid-left+1,right-mid)

if changedleftidx<=mid

if changedrightidx>mid

pushup(idx)//更新本節點資訊

}//查詢,查詢過程中有乙個很重要的操作便是懶惰標記的下推,理解了懶惰標記的下推,查詢操作就很好理解

func query(queryleft,queryright, left, right, idx int)int

var mid=left+(right-left)/2

pushdown(idx,mid-left+1,right-mid)

var res int

if queryleft<=mid

if queryright>mid

return res

}

參考:1,2

RMQ(線段樹實現)

t t第乙個線段樹程式,還沒a過題,不過也很感動,先貼出來 下標從0開始,輸入 1 1 結束.求每一段區間之間的最大值。include include typedef struct treenodenode int mymax int a,int b node buildtree int a,int...

線段樹簡單實現

首先,線段樹是一棵滿二叉樹。每個節點要麼有兩個孩子,要麼是深度相同的葉子節點 每個節點維護某個區間,根維護所有的。如圖,區間是二分父的區間。當有n個元素,初始化需要o n 時間,對區間操作需要o logn 時間。下面給出維護區間最小值的思路和 從下往上,每個節點的值為左右區間較小的那乙個即可。這算是...

線段樹(陣列實現)

最近看了很多學長髮的資料,吸取了別人的優點,把query函式更改的更加合理了。我是分割線 線段樹是一棵完美二叉樹,樹上的每個節點都維護乙個區間。根維護的是整個區間,每個節點維護的是父親的區間二等分後的其中乙個子區間。當有n個元素時,對區間的操作可以在o logn 的時間內完成。所以,線段樹是擅長處理...