數據結構-伸展樹
本文為轉載文章
作者:Vamei 出處:http://www.cnblogs.com/vamei 歡迎轉載,也請保留這段聲明。謝謝!
我們討論過,樹的搜索效率與樹的深度有關。二叉搜索樹的深度可能為n,這種情況下,每次搜索的復雜度為n的量級。AVL樹通過動態平衡樹的深度,單次搜索的復雜度為log(n) (以上參考紙上談兵 AVL樹)。我們下面看伸展樹(splay tree),它對於m次連續搜索操作有很好的效率。
伸展樹會在一次搜索後,對樹進行一些特殊的操作。這些操作的理念與AVL樹有些類似,即通過旋轉,來改變樹節點的分布,並減小樹的深度。但伸展樹並沒有AVL的平衡要求,任意節點的左右子樹可以相差任意深度。與二叉搜索樹類似,伸展樹的單次搜索也可能需要n次操作。但伸展樹可以保證,m次的連續搜索操作的復雜度為mlog(n)的量級,而不是mn量級。
具體來說,在查詢到目標節點後,伸展樹會不斷進行下面三種操作中的一個,直到目標節點成為根節點 (註意,祖父節點是指父節點的父節點)
1. zig: 當目標節點是根節點的左子節點或右子節點時,進行一次單旋轉,將目標節點調整到根節點的位置。
zig
2. zig-zag: 當目標節點、父節點和祖父節點成"zig-zag"構型時,進行一次雙旋轉,將目標節點調整到祖父節點的位置。
zig-zag
3. zig-zig:當目標節點、父節點和祖父節點成"zig-zig"構型時,進行一次zig-zig操作,將目標節點調整到祖父節點的位置。
zig-zig
單旋轉操作和雙旋轉操作見AVL樹。下面是zig-zig操作的示意圖:
zig-zig operation
在伸展樹中,zig-zig操作(基本上)取代了AVL樹中的單旋轉。通常來說,如果上面的樹是失衡的,那麽A、B子樹很可能深度比較大。相對於單旋轉(想一下單旋轉的效果),zig-zig可以將A、B子樹放在比較高的位置,從而減小樹總的深度。
下面我們用一個具體的例子示範。我們將從樹中搜索節點2:
Original
zig-zag (double rotation)
zig-zig
zig (single rotation at root)
上面的第一次查詢需要n次操作。然而經過一次查詢後,2節點成為了根節點,樹的深度大減小。整體上看,樹的大部分節點深度都減小。此後對各個節點的查詢將更有效率。
數據結構-伸展樹