BST, AVL Tree 和 Splay Tree 的实现

一、定义。

1.1 BST

  二叉搜索树,也称有序二叉树,排序二叉树,是指一棵空树或者具有下列性质的二叉树:

  ① 若任意节点的左子树不空,则左子树上所有结点的值均小于它的根结点的值;

  ② 若任意节点的右子树不空,则右子树上所有结点的值均大于它的根结点的值;

  ③ 任意节点的左、右子树也分别为二叉查找树。

  ④ 没有键值相等的节点。

1.2 AVL Tree

  平衡二叉树定义(AVL):它或者是一颗空树,或者具有以下性质的二叉树:它的左子树和右子树的深度之差(平衡因子)的绝对值不超过1,且它的左子树和右子树都是一颗平衡二叉树。

  平衡因子(bf):结点的左子树的深度减去右子树的深度。

  保持平衡是依赖于旋转操作,分为LL, RR, LR, RL四种情况。

  LL单旋即右旋。

  

1.3 Splay Tree

  伸展树的出发点是这样的:考虑到局部性原理(刚被访问的内容下次可能仍会被访问,查找次数多的内容可能下一次会被访问),为了使整个查找时间更小,被查频率高的那些节点应当经常处于靠近树根的位置。这样,很容易得想到以下这个方案:每次查找节点之后对树进行重构,把被查找的节点搬移到树根,这种自调整形式的二叉查找树就是伸展树。每次对伸展树进行操作后,它均会通过旋转的方法把被访问节点旋转到树根的位置。

  为了将当前被访问节点旋转到树根,我们通常将节点自底向上旋转,直至该节点成为树根为止。“旋转”的巧妙之处就是在不打乱数列中数据大小关系(指中序遍历结果是全序的)情况下,所有基本操作的平摊复杂度仍为O(log n)。

  伸展树主要有三种旋转操作,分别为单旋转,一字形旋转和之字形旋转。为了便于解释,我们假设当前被访问节点为X,X的父亲节点为Y(如果X的父亲节点存在),X的祖父节点为Z(如果X的祖父节点存在)。这里的单旋与之字形旋转与AVL树是一致的,因此这里只列出Zig-Zig。

  

  Splay操作可以自底向上也可以自顶向下,我只实现了自底向上的算法,自顶向下以后有机会再补充,因为每次操作都需要把操作的结点翻转到根,所以用Zig-Zig代替单旋,每次上升两层,如果根节点恰好是父节点,则此时只需要一次单旋。

二、复杂度分析。

  AVL无论是在顺序逆序或者随机插入删除的情况下效果都不错,而Splay在按照顺序或者逆序的情况下效果比较好,因为预测准确,而随机则无法预测,所做的Splay操作都是多余的,所以比较慢,AVL 和 Splay 哪个更合适需要具体情况具体分析。

2.1 BST

Algorithm   Average Worst case
Space   O(n) O(n)
Search   O(log n) O(n)
Insert   O(log n) O(n)
Delete   O(log n) O(n)

2.2 AVL Tree

Algorithm   Average Worst case
Space   O(n) O(n)
Search   O(log n) O(log n)
Insert   O(log n) O(log n)
Delete   O(log n) O(log n)

2.3 Splay Tree

Algorithm   Average Worst case
Space   O(n) O(n)
Search   O(log n) amortized O(log n)
Insert   O(log n) amortized O(log n)
Delete   O(log n) amortized O(log n)

三、实现。

  水平有限,写的比较啰嗦,见谅。

  1 #include <iostream>
  2 using namespace std;
  3 // Binery Search Tree Node
  4 class BSTreeNode {
  5 public:
  6     int data;
  7     BSTreeNode* leftChild;
  8     BSTreeNode* rightChild;
  9     BSTreeNode(int value): data(value), leftChild(NULL), rightChild(NULL){}
 10 };
 11 // AVL Tree Node
 12 class AVLTreeNode {
 13 public:
 14     int data;
 15     // The height of node
 16     int height;
 17     AVLTreeNode* leftChild;
 18     AVLTreeNode* rightChild;
 19     AVLTreeNode(int value): data(value), height(0), leftChild(NULL), rightChild(NULL){}
 20 };
 21 // Splay Tree Node
 22 class SplayTreeNode {
 23 public:
 24     int data;
 25     // The pointer to parent
 26     SplayTreeNode* parent;
 27     SplayTreeNode* leftChild;
 28     SplayTreeNode* rightChild;
 29     SplayTreeNode(int value): data(value), parent(NULL), leftChild(NULL), rightChild(NULL){}
 30 };
 31 // Preorder traversal
 32 void previsit(SplayTreeNode* T){
 33     if(T){
 34         cout<<T->data<<‘ ‘;
 35         previsit(T->leftChild);
 36         previsit(T->rightChild);
 37     }
 38
 39 }
 40 // Preorder traversal
 41 void previsit(BSTreeNode* T){
 42     if(T!=NULL){
 43         cout<<T->data<<‘ ‘;
 44         previsit(T->leftChild);
 45         previsit(T->rightChild);
 46     }
 47 }
 48 // Preorder traversal
 49 void previsit(AVLTreeNode* T){
 50     if(T){
 51             cout<<T->data<<‘ ‘;
 52             previsit(T->leftChild);
 53             previsit(T->rightChild);
 54     }
 55
 56 }
 57 // Find the minimun element
 58 BSTreeNode* BSTreeFindMin(BSTreeNode* T) {
 59     if (T == NULL) {
 60         return NULL;
 61     } else if (T->leftChild == NULL) {
 62         return T;
 63     } else {
 64         return BSTreeFindMin(T->leftChild);
 65     }
 66 }
 67 // Insert operation of Binery Search Tree
 68 BSTreeNode* BSTreeInsert(int value, BSTreeNode* T) {
 69     if (T == NULL) {
 70         T = new BSTreeNode(value);
 71     } else {
 72         // If value is smaller than element
 73         if (value < T->data) {
 74             T->leftChild = BSTreeInsert(value, T->leftChild);
 75         }
 76         // If value is larger than element
 77         else if (value > T->data) {
 78             T->rightChild = BSTreeInsert(value, T->rightChild);
 79         }
 80     }
 81     return T;
 82 }
 83 // Delete operation of Binery Search Tree
 84 BSTreeNode* BSTreeDelete(int value, BSTreeNode* T) {
 85     if (T == NULL) {
 86         return NULL;
 87     }
 88     // If value is smaller than element
 89     else if (value < T->data) {
 90         T->leftChild = BSTreeDelete(value, T->leftChild);
 91     }
 92     // If value is larger than element
 93     else if (value > T->data) {
 94         T->rightChild = BSTreeDelete(value, T->rightChild);
 95     }
 96     // If value is equal to element
 97     else {
 98         if (T->leftChild && T->rightChild) {
 99             // Two children
100             BSTreeNode* tmp = BSTreeFindMin(T->rightChild);
101             T->data = tmp->data;
102             //delete tmp;
103             T->rightChild = BSTreeDelete(T->data, T->rightChild);
104         } else {
105             // One or no child
106             if (T->leftChild) {
107                 T = T->leftChild;
108             } else if (T->rightChild) {
109                 T = T->rightChild;
110             } else {
111                 T = NULL;
112             }
113         }
114     }
115     return T;
116 }
117 // Get the height of AVL Tree
118 int getHeight(AVLTreeNode* T) {
119     if (T == NULL) {
120         return -1;
121     } else {
122         return T->height;
123     }
124 }
125 // Get the larger one element
126 int Max(int x, int y) {
127     return (x > y) ? x : y;
128 }
129 // LL Rotation
130 AVLTreeNode* SingleRotateWithLeft(AVLTreeNode* K2) {
131     AVLTreeNode* K1;
132
133     K1 = K2->leftChild;
134     K2->leftChild = K1->rightChild;
135     K1->rightChild = K2;
136
137     // Update the height of node
138     K2->height = Max(getHeight(K2->leftChild), getHeight(K2->rightChild)) + 1;
139     K1->height = Max(getHeight(K1->leftChild), getHeight(K1->rightChild)) + 1;
140     return K1;
141 }
142 // RR Rotation
143 AVLTreeNode* SingleRotateWithRight(AVLTreeNode* K2) {
144     AVLTreeNode* K1;
145
146     K1 = K2->rightChild;
147     K2->rightChild = K1->leftChild;
148     K1->leftChild = K2;
149
150     // Update the height of node
151     K2->height = Max(getHeight(K2->leftChild), getHeight(K2->rightChild)) + 1;
152     K1->height = Max(getHeight(K1->leftChild), getHeight(K1->rightChild)) + 1;
153     return K1;
154 }
155 // LR Rotation
156 AVLTreeNode* DoubleRotateWithLeft(AVLTreeNode* K3) {
157     K3->leftChild = SingleRotateWithRight(K3->leftChild);
158     return SingleRotateWithLeft(K3);
159 }
160 // RL Rotation
161 AVLTreeNode* DoubleRotateWithRight(AVLTreeNode* K3) {
162     K3->rightChild = SingleRotateWithLeft(K3->rightChild);
163     return SingleRotateWithRight(K3);
164 }
165 // Find the minimum element
166 AVLTreeNode* AVLTreeFindMin(AVLTreeNode* T) {
167     if (T == NULL) {
168         return NULL;
169     } else if (T->leftChild == NULL) {
170         return T;
171     } else {
172         return AVLTreeFindMin(T->leftChild);
173     }
174 }
175 // Insert operation of AVL Tree
176 AVLTreeNode* AVLTreeInsert(int value, AVLTreeNode* T) {
177     if (T == NULL) {
178         T = new AVLTreeNode(value);
179         return T;
180     } else {
181         // If value is smaller than element
182         if (value < T->data) {
183             T->leftChild = AVLTreeInsert(value, T->leftChild);
184             // If the balance is broken
185             if (getHeight(T->leftChild) - getHeight(T->rightChild) == 2) {
186                 if (value < T->leftChild->data) {
187                     // LL Rotation
188                     T = SingleRotateWithLeft(T);
189                 } else {
190                     // LR Rotation
191                     T = DoubleRotateWithLeft(T);
192                 }
193             }
194         }
195         // If value is larger than element
196         else if (value > T->data) {
197             T->rightChild = AVLTreeInsert(value, T->rightChild);
198             // If the balance is broken
199             if (getHeight(T->rightChild) - getHeight(T->leftChild) == 2) {
200                 if (value > T->rightChild->data) {
201                     // RR Rotation
202                     T = SingleRotateWithRight(T);
203                 } else {
204                     // RL Rotation
205                     T = DoubleRotateWithRight(T);
206                 }
207             }
208         }
209
210         // Update the height of node
211         if (T) {
212             T->height = Max(getHeight(T->leftChild), getHeight(T->rightChild)) + 1;
213         }
214         return T;
215     }
216 }
217 // Delete operation of AVL Tree
218 AVLTreeNode* AVLTreeDelete(int value, AVLTreeNode* T) {
219     if (T == NULL) {
220         return NULL;
221     } else {
222         // If value is smaller than element
223         if (value < T->data) {
224             T->leftChild = AVLTreeDelete(value, T->leftChild);
225             // If the balance is broken
226             if (getHeight(T->rightChild) - getHeight(T->leftChild) == 2) {
227                 // Delete is similar to insert
228                 // We can assume the unbalance is caused by insert an element
229                 if (getHeight(T->rightChild->rightChild) >= getHeight(T->rightChild->leftChild)) {
230                     // RR Rotation
231                     T = SingleRotateWithRight(T);
232                 } else {
233                     // RL Rotation
234                     T = DoubleRotateWithRight(T);
235                 }
236             }
237         }
238         // If value is larger than element
239         else if (value > T->data) {
240             T->rightChild = AVLTreeDelete(value, T->rightChild);
241             // If the balance is broken
242             if (getHeight(T->leftChild) - getHeight(T->rightChild) == 2) {
243                 // Delete is similar to insert
244                 // We can assume the unbalance is caused by insert an element
245                 if (getHeight(T->leftChild->leftChild) >= getHeight(T->leftChild->rightChild)) {
246                     // LL Rotation
247                     T = SingleRotateWithLeft(T);
248                 } else {
249                     // LR Rotation
250                     T = DoubleRotateWithLeft(T);
251                 }
252             }
253         }
254         // If value is equal to element
255         else {
256             if (T->leftChild && T->rightChild) {
257                 // Two children
258                 AVLTreeNode* tmp = AVLTreeFindMin(T->rightChild);
259                 T->data = tmp->data;
260                 //delete tmp;
261                 T->rightChild = AVLTreeDelete(T->data, T->rightChild);
262             } else {
263                 // One or no child
264                 if (T->leftChild) {
265                     T = T->leftChild;
266                 } else if (T->rightChild) {
267                     T = T->rightChild;
268                 } else {
269                     T = NULL;
270                 }
271             }
272         }
273     }
274
275     // Update the height of node
276     if (T) {
277         T->height = Max(getHeight(T->leftChild), getHeight(T->rightChild)) + 1;
278     }
279     return T;
280 }
281 // LL Rotation of Splay Tree
282 SplayTreeNode* SplaySingleRotateWithLeft(SplayTreeNode* K2) {
283     // It is similar to AVL Tree
284     // But we must update the parent of node
285     SplayTreeNode* K1 = K2->leftChild;
286     SplayTreeNode* P = K2->parent;
287     K2->leftChild = K1->rightChild;
288     if(K2->leftChild){
289         K2->leftChild->parent = K2;
290     }
291     K1->rightChild = K2;
292     K1->rightChild->parent = K1;
293     K1->parent = P;
294     if (P != NULL) {
295         if (P->leftChild == K2) {
296             P->leftChild = K1;
297         } else {
298             P->rightChild = K1;
299         }
300     }
301     return K1;
302 }
303 // RR Rotation of Splay Tree
304 SplayTreeNode* SplaySingleRotateWithRight(SplayTreeNode* K2) {
305     // It is similar to AVL Tree
306     // But we must update the parent of node
307     SplayTreeNode* K1 = K2->rightChild;
308     SplayTreeNode* P = K2->parent;
309     K2->rightChild = K1->leftChild;
310     if(K2->rightChild){
311         K2->rightChild->parent = K2;
312     }
313     K1->leftChild = K2;
314     if(K1->leftChild){
315         K1->leftChild->parent = K1;
316     }
317
318     K1->parent = P;
319     if (P != NULL) {
320         if (P->leftChild == K2) {
321             P->leftChild = K1;
322         } else {
323             P->rightChild = K1;
324         }
325     }
326     return K1;
327 }
328 // LR Rotation
329 SplayTreeNode* SplayDoubleRotateWithLeft(SplayTreeNode* K3) {
330     K3->leftChild = SplaySingleRotateWithRight(K3->leftChild);
331     return SplaySingleRotateWithLeft(K3);
332 }
333 // RL Rotation
334 SplayTreeNode* SplayDoubleRotateWithRight(SplayTreeNode* K3) {
335     K3->rightChild = SplaySingleRotateWithLeft(K3->rightChild);
336     return SplaySingleRotateWithRight(K3);
337 }
338 // L-Zig-Zig
339 SplayTreeNode* ZigZigWithLeft(SplayTreeNode* K3) {
340     SplayTreeNode* parent = K3->parent;
341     SplayTreeNode* K2 = K3->leftChild;
342     SplayTreeNode* K1 = K2->leftChild;
343
344     K3->leftChild = K2->rightChild;
345     if (K2->rightChild != NULL) {
346         K3->leftChild->parent = K3;
347     }
348     K2->rightChild = K3;
349     K2->rightChild->parent = K2;
350     K2->leftChild = K1->rightChild;
351     if (K1->rightChild != NULL) {
352         K2->leftChild->parent = K2;
353     }
354     K1->rightChild = K2;
355     K1->rightChild->parent = K1;
356     K1->parent = parent;
357     if (parent != NULL) {
358         if (parent->leftChild == K3) {
359             parent->leftChild = K1;
360         } else {
361             parent->rightChild = K1;
362         }
363     }
364     return K1;
365 }
366 // R-Zig-Zig
367 SplayTreeNode* ZigZigWithRight(SplayTreeNode* K3) {
368     SplayTreeNode* parent = K3->parent;
369     SplayTreeNode* K2 = K3->leftChild;
370     SplayTreeNode* K1 = K2->leftChild;
371
372     K3->rightChild = K2->leftChild;
373     if (K2->leftChild != NULL) {
374         K3->rightChild->parent = K3;
375     }
376     K2->leftChild = K3;
377     K2->leftChild->parent = K2;
378     K2->rightChild = K1->leftChild;
379     if (K1->leftChild != NULL) {
380         K2->rightChild->parent = K2;
381     }
382     K1->leftChild = K2;
383     K1->leftChild->parent = K1;
384     K1->parent = parent;
385     if (parent != NULL) {
386         if (parent->leftChild == K3) {
387             parent->leftChild = K1;
388         } else {
389             parent->rightChild = K1;
390         }
391     }
392     return K1;
393 }
394 // Insert operation of Splay Tree without Splay
395 // It is similar to insert operation of Binery Search Tree
396 SplayTreeNode* PreInsert(int value, SplayTreeNode* T) {
397     if (T == NULL) {
398         T = new SplayTreeNode(value);
399     } else {
400         if (value < T->data) {
401             T->leftChild = PreInsert(value, T->leftChild);
402             // Update the parent of node
403             T->leftChild->parent = T;
404         } else if (value > T->data) {
405             T->rightChild = PreInsert(value, T->rightChild);
406             // Update the parent of node
407             T->rightChild->parent = T;
408         }
409     }
410     return T;
411 }
412 // Find the maximum element
413 SplayTreeNode* SplayTreeFindMax(SplayTreeNode* T) {
414     if (T == NULL) {
415         return NULL;
416     } else if (T->rightChild == NULL) {
417         return T;
418     } else {
419         return SplayTreeFindMax(T->rightChild);
420     }
421 }
422 // Find the minimum element
423 SplayTreeNode* SplayTreeFindMin(SplayTreeNode* T) {
424     if (T == NULL) {
425         return NULL;
426     } else if (T->leftChild == NULL) {
427         return T;
428     } else {
429         return SplayTreeFindMin(T->leftChild);
430     }
431 }
432 // Find the element and return the node
433 SplayTreeNode* Find(int value, SplayTreeNode* T) {
434     if (T == NULL) {
435         return NULL;
436     } else if (T->data == value) {
437         return T;
438     } else if (T->data > value) {
439         return Find(value, T->leftChild);
440     } else {
441         return Find(value, T->rightChild);
442     }
443 }
444 // Splay operation of Splay Tree
445 SplayTreeNode* Splay(int value, SplayTreeNode* T) {
446     SplayTreeNode* K = Find(value, T);
447     // Parent node
448     SplayTreeNode* P = NULL;
449     // Grandparent node
450     SplayTreeNode* GP = NULL;
451     // If node doesn‘t exist
452     if (K == NULL) {
453         return T;
454     }
455     // Do rotation until K arrives at root or is the child of root
456     while (T->leftChild != K && T->rightChild != K) {
457         P = K->parent;
458         // Break the loop if just need single rotation
459         if(P==NULL||P->parent==NULL){
460             break;
461         }
462         GP = P->parent;
463         if (GP->leftChild == P && P->leftChild == K) {
464             // L-Zig-Zig
465             ZigZigWithLeft(GP);
466         } else if (GP->leftChild == P && P->rightChild == K) {
467             // LR Rotation
468             SplayDoubleRotateWithLeft(GP);
469         } else if (GP->rightChild == P && P->leftChild == K) {
470             // RL Rotation
471             SplayDoubleRotateWithRight(GP);
472         } else if (GP->rightChild == P && P->rightChild == K) {
473             // R-Zig-Zig
474             ZigZigWithRight(GP);
475         }
476         // Return the new root if GP == T
477         if(GP == T){
478             return K;
479         }
480     }
481     if (T->leftChild == K) {
482         // LL Rotation
483         T = SplaySingleRotateWithLeft(T);
484     } else if (T->rightChild == K) {
485         // RR Rotation
486         T = SplaySingleRotateWithRight(T);
487     }
488     return T;
489 }
490 // Insert operation of Splay Tree
491 SplayTreeNode* SplayTreeInsert(int value, SplayTreeNode* T) {
492     // First insert the element just like Binery Search Tree
493     T = PreInsert(value, T);
494     // Then do the Splay
495     T = Splay(value, T);
496 }
497 // Splay operation of Splay Tree
498 SplayTreeNode* Splay(SplayTreeNode* node, SplayTreeNode* T) {
499       SplayTreeNode* K = node;
500     // Parent node
501     SplayTreeNode* P = NULL;
502     // Grandparent node
503     SplayTreeNode* GP = NULL;
504     // If node doesn‘t exist
505     if(K == NULL){
506         return T;
507     }
508     // Do rotation until K arrives at root or is the child of root
509     while (T->leftChild != K && T->rightChild != K) {
510         P = K->parent;
511         // Break the loop if just need single rotation
512         if(P==NULL||P->parent==NULL){
513             break;
514         }
515         GP = P->parent;
516         if (GP->leftChild == P && P->leftChild == K) {
517             // L-Zig-Zig
518             ZigZigWithLeft(GP);
519         } else if (GP->leftChild == P && P->rightChild == K) {
520             // LR Rotation
521             SplayDoubleRotateWithLeft(GP);
522         } else if (GP->rightChild == P && P->leftChild == K) {
523             // RL Rotation
524             SplayDoubleRotateWithRight(GP);
525         } else if (GP->rightChild == P && P->rightChild == K) {
526             // R-Zig-Zig
527             ZigZigWithRight(GP);
528         }
529         // Return the new root if GP == T
530         if(GP == T){
531             return K;
532         }
533     }
534     if (T->leftChild == K) {
535         // LL Rotation
536         T = SplaySingleRotateWithLeft(T);
537     } else if (T->rightChild == K) {
538         // RR Rotation
539         T = SplaySingleRotateWithRight(T);
540     }
541     return T;
542 }
543 // Delete operation of Splay Tree
544 SplayTreeNode* SplayTreeDelete(int value, SplayTreeNode* T) {
545     // If T is NULL
546     if (!T) {
547         return NULL;
548     }
549     // First do the Splay operation
550     T = Splay(value, T);
551     // Leftchild of root
552     SplayTreeNode* L = T->leftChild;
553     // Rightchild of root
554     SplayTreeNode* R = T->rightChild;
555     // If the tree doesn‘t have rightchild
556     if(R==NULL){
557         R = L;
558         if (L) {
559             R->parent = NULL;
560         }
561     }
562     else{
563         R->parent = NULL;
564         // Find the minimum element of R
565         R = Splay(SplayTreeFindMin(R), R);
566         R-> leftChild = L;
567         if(L){
568             L->parent = R;
569         }
570     }
571     // Delete the element
572     delete T;
573     return R;
574 }

原文地址:https://www.cnblogs.com/lyf520/p/8684293.html

时间: 2024-08-25 15:52:32

BST, AVL Tree 和 Splay Tree 的实现的相关文章

各种平衡树Treap/SBT/Avl/Splay tree

看了这么久的平衡树,是时候做个总结了. 以poj 3481为例,敲了四份代码,分别是Treap ,Size Balance Tree,Avl Tree,splay tree. 唯独少了红黑树T_T... 总的来说每种平衡树各有各的优点吧: Treap写起来简单上手也快如果熟练的话不到十分种可以敲完. SBT速度快名不虚传... Avl树高度平衡吧,不过实际的效果不尽如人意,可能是我实现的姿势不对吧/(ㄒoㄒ)/~~ splay tree各方面比较均衡,特别的伸展树在维护序列方面相对其它几种树优势

【430】BST and Splay Tree

参考:Hello, Splay! 目录: 1. Binary Search Tree 2. Splay Tree 原文地址:https://www.cnblogs.com/alex-bn-lee/p/11330459.html

Splay Tree

伸展树 和AVL树不一样,伸展树并不保证每次操作的时间复杂度为O(logn),而保证任何一个m个操作的序列总时间为O(mlogn).伸展树的基本思想是:每个结点被访问时,使用AVL树的旋转操作把它移动到根.由于旋转是自底向上的,所以需要设置父亲指针,而不像AVL树那样以儿子为轴旋转.伸展操作(splaying) 伸展树的核心是伸展操作Splay(x,S).它是在保持伸展树有序性的前提下,通过一系列旋转将伸展树S中的元素x调整到树的根部.在调整的过程中,要根据x的位置分以下三种情况分别处理.情况一

【BBST 之伸展树 (Splay Tree)】

最近“hiho一下”出了平衡树专题,这周的Splay一直出现RE,应该删除操作指针没处理好,还没找出原因. 不过其他操作运行正常,尝试用它写了一道之前用set做的平衡树的题http://codeforces.com/problemset/problem/675/D,运行效果居然还挺好的,时间快了大概10%,内存少了大概30%. 1 #include <cstdio> 2 #include <cstring> 3 #include <string> 4 #include

Geeks Splay Tree Insert 树的插入操作

Splay树的插入操作,只需要处理好插入节点的孩子节点就可以了,最重要的是不要破坏了BST的基本规则. 因为高度并不是Splay树的首要因素,所以插入的时候也是使用splay操作,然后在根节点插入. 参考:http://www.geeksforgeeks.org/splay-tree-set-2-insert-delete/ 对比一下使用插入创建的树和手工创建数的区别,先序遍历的结果: #pragma once #include<stdio.h> #include <stdlib.h&g

树-伸展树(Splay Tree)

伸展树概念 伸展树(Splay Tree)是一种二叉排序树,它能在O(log n)内完成插入.查找和删除操作.它由Daniel Sleator和Robert Tarjan创造. (01) 伸展树属于二叉查找树,即它具有和二叉查找树一样的性质:假设x为树中的任意一个结点,x节点包含关键字key,节点x的key值记为key[x].如果y是x的左子树中的一个结点,则key[y] <= key[x]:如果y是x的右子树的一个结点,则key[y] >= key[x]. (02) 除了拥有二叉查找树的性质

Splay Tree(伸展树)

参考:<数据结构(C++语言版)>邓俊辉著 (好书 一. 伸展树(由 D. D. Sleator 和 R. E. Tarjan 于 1985 年发明)也是平衡二叉搜索树的一种形式.相对于 AVL 树,伸展树的实现更为简洁 伸展树无需时刻都严格地保持全树的平衡,但却能够在任何足够长的真实操作序列中,保持分摊意义上的高效率 伸展树也不需要对基本的二叉树节点结构做任何附加的要求或改动,更不需要记录平衡因子或高度之类的额外信息,故适用范围更广 二.局部性 信息处理的典型模式是,将所有的数据项视作一个集

[转] Splay Tree(伸展树)

好久没写过了,比赛的时候就调了一个小时,差点悲剧,重新复习一下,觉得这个写的很不错.转自:here Splay Tree(伸展树) 二叉查找树(Binary Search Tree)能够支持多种动态集合操作.因此,在信息学竞赛中,二叉排序树起着非常重要的作用,它可以被用来表示有序集合.建立索引或优先队列等. 作用于二叉查找树上的基本操作的时间是与树的高度成正比的.对一个含n各节点的完全二叉树,这些操作的最坏情况运行时间为O(log n).但如果树是含n个节点的线性链,则这些操作的最坏情况运行时间

BZOJ 1588:splay tree

刚学习的splay tree.照着大神的代码敲了敲,理解了个大概 很好用的数据结构,可以用来维护数列 学习时建议先看看SBT,这样可以更好地理解“旋转” #include"cstdio" #include"queue" #include"cmath" #include"stack" #include"iostream" #include"algorithm" #include"