線段樹是一顆平衡的二叉搜尋樹,他以空間換區時間,讓線性查詢加速log級別的查詢,用到的演算法主要是二分搜尋和遞迴。
例如:有陣列data=, 我有乙個需求,我需要頻繁的查詢區間i~j的sum和。這裡先給出兩個解決方案:
如果使用最普通的演算法遍歷,那麼查詢和更新的複雜度為o(n)。
當然你還可以使用動態規劃,定義dp陣列為dp[i][j] ,意義為從i~j的sum和,但是更新某個資料的複雜度也是o(n)。
又或者定義dp陣列為dp[i], 意義為從0~i的sum和,同理更新的複雜度也是o(n)。
線段樹圖示
如果我們有辦法構建圖示這樣的樹,那麼查詢和更新都可以log(n)搞定。
首先我們考慮乙個問題,構建這樣的一棵樹所需要的樹節點個數與data的長度有什麼關聯,也就是說我的樹節點應該開多少空間,第一棵樹是一顆滿二叉樹,因為data正好是2的k次方,這樣樹的節點個數為2的k次方-1,最後一層的個數正好是上面所有層的節點個數+1,所有對於這種滿二叉樹節點個數開2倍data.length足夠了,對於右邊圖,開4倍data.length足夠了
buildsegmenttree圖示
;}//以treeindex為根構建從left到right的線段樹
private
void
buildsegmenttree
(int treeindex,
int left,
int right)
int mid = left+
(right-left)/2
;int leftindex =
leftindex
(treeindex)
;int rightindex =
rightindex
(treeindex)
;buildsegmenttree
(leftindex,left,mid)
;buildsegmenttree
(rightindex,mid+
1,right)
; tree[treeindex]
= merger.
merge
(tree[leftindex]
,tree[rightindex]);
}//查詢
public e query
(int queryl,
int queryr)
//以treeindex為根從範圍l-r查詢queryl到queryr的線段樹的merger值
private e query
(int treeindex,
int queryl,
int queryr,
int l,
int r)
int mid = l+
(r-l)/2
;int leftindex =
leftindex
(treeindex)
;int rightindex =
rightindex
(treeindex)
;//左邊
if(queryr<=mid)
//右邊
else
if(queryl>mid)
else
}//更新
public
void
set(
int index,e e)
private
void
set(
int treeindex,
int l,
int r,
int index, e e)
int mid = l+
(r-l)/2
;int leftindex =
leftindex
(treeindex)
;int rightindex =
rightindex
(treeindex)
;//右邊更新
if(index>mid)
else
tree[treeindex]
= merger.
merge
(tree[leftindex]
,tree[rightindex]);
}private
void
checkindex
(int index)
}public
intleftindex
(int index)
public
intrightindex
(int index)
}
public
inte***ce
merger
public
class
testsegment
; segmenttree
tree =
newsegmenttree
<
>
(data,
(a,b)
->);
system.out.
println
(tree.
query(1
,3))
; tree.
set(2,
10); system.out.
println
(tree.
query(1
,3));}}
資料結構 線段樹
啦啦啦啦啦啦線段樹是個好東西 好吧並沒有什麼好的 但貌似還是很好啊 線段樹就是一棵樹!顧名思義 又是這個詞 就是求關於一段的某些什麼什麼東西。比如區間最大值啊什麼的。引用百科知識 線段樹是一種二叉搜尋樹,與區間樹相似,它將乙個區間劃分成一些單元區間,每個單元區間對應線段樹中的乙個葉結點。對於線段樹中...
資料結構 線段樹
一 目標 1.如何快速的查詢出下列陣列arr 2,5 的和 2。以及更新arr 4 為6。用普通的方法查詢的複雜度為o n 更新的複雜度為o 1 這時候我們可以用線段樹來快速完成這些操作,複雜度為logn。二 內容 如何建立,查詢,更新線段樹。public class qurqpd int tree...
資料結構 線段樹
摘自 演算法競賽高階指南 線段樹是一種基於分治思想的二叉樹結構,用於在區間上進行資訊統計。線段樹的基本特徵 1.線段樹的每個節點都代表乙個區間。2.線段樹具有唯一的根節點,代表的區間是整個統計範圍,如 1,n 3.線段樹的每個葉節點都代表乙個長度為1的元區間 x,x 4.對於每個內部節點 l,r 它...