平衡有序二叉树(AVL Tree)的C++实现

  平衡二叉树是一个重要的数据结构,它有很均衡的插入、删除以及查询性能(时间复杂度都是O(logn))。Linux2.4以前的内核中,虚拟内存管理中用的容器就是AVL Tree,之后的版本都改成了RBTree即红黑树。AVL Tree对平衡的要求是比较严格的,它要求左右子数之间的长度差不能大于1,也正由于它的严格导致了AVL Tree的统计性能没有RBTree好。AVL Tree在插入或者删除节点时候出现不平衡情况,根据具体情况进行一次或者多次单旋或者双旋就可以使整棵树达到平衡。具体的旋转规则看这里,删除节点的算法看这里。下面是我根据AVL树的规则用C++实现的代码:

  1 #ifndef        __AVLTREE_H__
  2 #define        __AVLTREE_H__
  3 
  4 #include <stdlib.h>
  5 #include <iostream>
  6 
  7 struct AVLNode
  8 {
  9     int nData;
 10     AVLNode* pLeft;
 11     AVLNode* pRight;
 12     AVLNode* pParent;
 13     int nHeight;
 14 };
 15 
 16 class AVLTree
 17 {
 18 public:
 19     AVLTree() : pRoot(NULL), nNodeCount(0){}
 20     ~AVLTree(){ DeleteTree(&pRoot); }
 21 public:
 22     int Insert(int nData);
 23     int Delete(int nData);
 24     int Find(int nData) const;
 25     int GetNodeCount() const;
 26     void Display() const;
 27 
 28 private:
 29     int Max(int a, int b) const;
 30     int Height(const AVLNode* pNode) const;
 31     AVLNode* CreateNode(int nData);
 32     AVLNode* DeleteNode(int nData, AVLNode* pNode);
 33     AVLNode* BalanceAdjust(AVLNode* pNode);
 34     AVLNode* RotateLeft(AVLNode* pNode);
 35     AVLNode* RotateRight(AVLNode* pNode);
 36     AVLNode* RotateLeftRight(AVLNode* pNode);
 37     AVLNode* RotateRightLeft(AVLNode* pNode);
 38     void DeleteTree(AVLNode** ppRoot);
 39     void PrintTree(AVLNode* pNode) const;
 40 
 41     AVLTree(const AVLTree&) {}
 42     AVLTree& operator=(const AVLTree&) {}
 43 
 44 private:
 45     AVLNode* pRoot;
 46     int nNodeCount;
 47 };
 48 
 49 int AVLTree::Max(int a, int b) const
 50 {
 51     return (a > b ? a : b);
 52 }
 53 
 54 int AVLTree::Height(const AVLNode* pNode) const
 55 {
 56     if (NULL == pNode)
 57         return -1;
 58 
 59     return pNode->nHeight;
 60 }
 61 
 62 int AVLTree::Insert(int nData)
 63 {
 64     if(pRoot == NULL)
 65     {
 66         pRoot = CreateNode(nData);
 67 
 68         return nNodeCount;
 69     }
 70 
 71     AVLNode* pInsertNode = pRoot;
 72 
 73     while(pInsertNode != NULL)
 74     {
 75         if(nData < pInsertNode->nData)
 76         {
 77             if(pInsertNode->pLeft == NULL)
 78             {
 79                 pInsertNode->pLeft = CreateNode(nData);
 80                 pInsertNode->pLeft->pParent = pInsertNode;
 81 
 82                 pRoot = BalanceAdjust(pInsertNode->pLeft);
 83                 break;
 84             }
 85 
 86             pInsertNode = pInsertNode->pLeft;
 87         }
 88         else if(nData > pInsertNode->nData)
 89         {
 90             if(pInsertNode->pRight == NULL)
 91             {
 92                 pInsertNode->pRight = CreateNode(nData);
 93                 pInsertNode->pRight->pParent = pInsertNode;
 94 
 95                 pRoot = BalanceAdjust(pInsertNode->pRight);
 96                 break;
 97             }
 98 
 99             pInsertNode = pInsertNode->pRight;
100         }
101         else
102         {
103             return nNodeCount;
104         }
105     }
106 
107     return nNodeCount;
108 }
109 
110 int AVLTree::Delete(int nData)
111 {
112     //std::cout << "Delete nData = " << nData << std::endl;
113     //std::cout << "pNode->nData = " << pNode->nData << std::endl;
114     //std::cout << "pPNode->nData = " << pPNode->nData << std::endl;
115 
116     AVLNode* pCurNode = pRoot;
117 
118     while(pCurNode != NULL)
119     {
120         if(nData > pCurNode->nData)
121         {
122             pCurNode = pCurNode->pRight;
123         }
124         else if(nData < pCurNode->nData)
125         {
126             pCurNode = pCurNode->pLeft;
127         }
128         else
129         {
130             pRoot = DeleteNode(nData, pCurNode);
131             break;
132         }
133     }
134 
135 
136     if(pCurNode == NULL)
137         std::cout << "没有找到元素 nData = " << nData << std::endl;
138     //int x;
139     //std::cin >> x;
140 
141     return nNodeCount;//没有找到要删除的元素    
142 }
143 
144 AVLNode* AVLTree::DeleteNode(int nData, AVLNode* pNode)
145 {
146     nNodeCount--;
147 
148     if(pNode->pLeft && pNode->pRight)//删除节点有左右子树
149     {
150         AVLNode* pLMaxNode = pNode->pLeft;//删除节点左子树中最大的节点
151         AVLNode* pLMaxPNode = pNode;//删除节点左子树中最大节点的父节点
152 
153         //将删除节点左孩子的最大节点替换删除节点,然后删除该节点
154         if(pLMaxNode->pRight == NULL)
155         {
156             pNode->nData = pLMaxNode->nData;
157             pNode->pLeft = pLMaxNode->pLeft;
158 
159             if(pLMaxNode->pLeft != NULL)
160                 pLMaxNode->pLeft->pParent = pNode;
161         }
162         else
163         {
164             while(pLMaxNode->pRight)
165             {
166                 pLMaxPNode = pLMaxNode;
167                 pLMaxNode = pLMaxNode->pRight;
168             }
169             pNode->nData = pLMaxNode->nData;
170 
171             if(pLMaxNode == pLMaxPNode->pRight)//将替换后的删除节点删除
172                 pLMaxPNode->pRight = pLMaxNode->pLeft;
173             else if(pLMaxNode == pLMaxPNode->pLeft)
174                 pLMaxPNode->pLeft = NULL;
175         }
176         
177         delete pLMaxNode;
178 
179         return BalanceAdjust(pLMaxPNode);
180     }
181     else if(pNode->pLeft)//删除节点只有左子树
182     {
183         AVLNode* pLeft = pNode->pLeft;
184 
185         pNode->nData = pLeft->nData;
186 
187         pNode->pLeft = pLeft->pLeft;
188         if (pLeft->pLeft != NULL)
189             pLeft->pLeft->pParent = pNode;
190 
191         pNode->pRight = pLeft->pRight;
192         if (pLeft->pRight != NULL)
193             pLeft->pRight->pParent = pNode;
194         
195         delete pLeft;
196 
197         return BalanceAdjust(pNode);
198     }
199     else if(pNode->pRight)//删除节点只有右子树
200     {
201         AVLNode* pRight = pNode->pRight;
202 
203         pNode->nData = pRight->nData;
204 
205         pNode->pLeft = pRight->pLeft;
206         if (pRight->pLeft != NULL)
207             pRight->pLeft->pParent = pNode;
208 
209         pNode->pRight = pRight->pRight;
210         if (pRight->pRight != NULL)
211             pRight->pRight->pParent = pNode;
212         
213         delete pRight;
214 
215         return BalanceAdjust(pNode);
216     }
217     else//删除节点没有子树
218     {
219         AVLNode* pPNode = pNode->pParent;
220 
221         if(pPNode->pLeft == pNode)
222             pPNode->pLeft = NULL;
223         else if(pPNode->pRight == pNode)
224             pPNode->pRight = NULL;
225 
226         delete pNode;
227 
228         return BalanceAdjust(pPNode);
229     }
230 }
231 
232 AVLNode* AVLTree::BalanceAdjust(AVLNode* pNode)
233 {
234     AVLNode* pRoot;
235     AVLNode* pPNode;
236     
237     while(pNode != NULL)//删除节点的子节点进行平衡
238     {
239         pPNode = pNode->pParent;
240 
241         bool bIsLeft = false;
242         if(pPNode != NULL && pNode == pPNode->pLeft)
243             bIsLeft = true;
244 
245         pNode->nHeight = Max(Height(pNode->pLeft), Height(pNode->pRight)) + 1;
246 
247         if (Height(pNode->pLeft) - Height(pNode->pRight) == 2)    // AVL树不平衡  执行LL型或者LR型旋转
248         {
249             if (Height(pNode->pLeft->pLeft) - Height(pNode->pLeft->pRight) == -1)
250                 pNode = RotateLeftRight(pNode);
251             else 
252                 pNode = RotateLeft(pNode);
253 
254             if(pPNode != NULL && bIsLeft)
255                 pPNode->pLeft = pNode;
256             else if(pPNode != NULL)
257                 pPNode->pRight = pNode;
258         }
259         else if(Height(pNode->pLeft) - Height(pNode->pRight) == -2)    // AVL树不平衡  执行RR型或者RL型旋转
260         {
261             if (Height(pNode->pRight->pLeft) - Height(pNode->pRight->pRight) == 1)
262                 pNode = RotateRightLeft(pNode);
263             else
264                 pNode = RotateRight(pNode);
265 
266             if (pPNode != NULL && bIsLeft)
267                 pPNode->pLeft = pNode;
268             else if(pPNode != NULL)
269                 pPNode->pRight = pNode;
270         }
271 
272         pRoot = pNode;
273         pNode = pPNode;
274     }
275 
276     return pRoot;
277 }
278 
279 AVLNode* AVLTree::CreateNode(int nData)
280 {
281     nNodeCount++;
282 
283     AVLNode* pNewNode = new AVLNode();
284     pNewNode->nData = nData;
285     pNewNode->nHeight = 0;
286     pNewNode->pLeft = pNewNode->pRight = NULL;
287 
288     return pNewNode;
289 }
290 
291 int AVLTree::Find(int nData) const
292 {
293     AVLNode* pFindNode = pRoot;
294     while(pFindNode)
295     {
296         if(nData < pFindNode->nData)
297             pFindNode = pFindNode->pLeft;
298         else if(nData > pFindNode->nData)
299             pFindNode = pFindNode->pRight;
300         else
301             return pFindNode->nData;
302     }
303     
304     return -1;
305 }
306 
307 AVLNode* AVLTree::RotateLeft(AVLNode* pNode)//左单
308 {
309     AVLNode* pLeftChild;
310 
311     pLeftChild = pNode->pLeft;
312     pNode->pLeft = pLeftChild->pRight;
313     pLeftChild->pRight = pNode;
314 
315     pLeftChild->pParent = pNode->pParent;
316     pNode->pParent = pLeftChild;
317 
318     if(pNode->pLeft)
319         pNode->pLeft->pParent = pNode;
320 
321     // 结点的位置改变,节点高度要重新计算
322     pNode->nHeight = Max(Height(pNode->pLeft), Height(pNode->pRight)) + 1;
323     pLeftChild->nHeight = Max(Height(pLeftChild->pLeft), pNode->nHeight) + 1;
324 
325     return pLeftChild;
326 }
327 
328 AVLNode* AVLTree::RotateRight(AVLNode* pNode)//右单
329 {
330     AVLNode* pRightChild;
331 
332     pRightChild = pNode->pRight;
333     pNode->pRight = pRightChild->pLeft;
334     pRightChild->pLeft = pNode;
335 
336     pRightChild->pParent = pNode->pParent;
337     pNode->pParent = pRightChild;
338 
339     if(pNode->pRight)
340         pNode->pRight->pParent = pNode;
341 
342     // 结点的位置改变,节点高度要重新计算
343     pNode->nHeight = Max(Height(pNode->pLeft), Height(pNode->pRight)) + 1;
344     pRightChild->nHeight = Max(Height(pRightChild->pRight), pNode->nHeight) + 1;
345 
346     return pRightChild;
347 }
348 
349 AVLNode* AVLTree::RotateLeftRight(AVLNode* pNode)//左双
350 {
351     pNode->pLeft = RotateRight(pNode->pLeft);
352 
353     return RotateLeft(pNode);
354 }
355 
356 AVLNode* AVLTree::RotateRightLeft(AVLNode* pNode)//右双
357 {
358     pNode->pRight = RotateLeft(pNode->pRight);
359 
360     return RotateRight(pNode);
361 }
362 
363 // 后序遍历树以删除树
364 void AVLTree::DeleteTree(AVLNode** ppRoot)
365 {
366     if (NULL == ppRoot || NULL == *ppRoot)
367         return;
368 
369     DeleteTree(&((*ppRoot)->pLeft));
370     DeleteTree(&((*ppRoot)->pRight));
371     delete *ppRoot;
372     *ppRoot = NULL;
373 }
374 
375 int AVLTree::GetNodeCount() const
376 {
377     return nNodeCount;
378 }
379 
380 void AVLTree::Display() const
381 {
382      PrintTree(this->pRoot);
383 }
384 
385 void AVLTree::PrintTree(AVLNode* pNode) const
386 {
387     if (NULL == pRoot)
388         return;
389 
390     if (NULL == pNode)
391     {
392         return;
393     }
394 
395     static int n = 0;
396     
397     if(pNode == pRoot)
398     {
399         std::cout << "[" << ++n << "]nData = " << pNode->nData << ",nParentData= 0 ,";
400 
401         if(pNode->pLeft)
402             std::cout << "nLeftData= " << pNode->pLeft->nData << " ,";
403         if(pNode->pRight)
404             std::cout << "nRightData= " << pNode->pRight->nData << " ,";
405 
406         std::cout << "nHeight = " << pNode->nHeight << std::endl;
407     }
408     else
409     {
410         std::cout << "[" << ++n << "]nData = " << pNode->nData << ",nParentData= " << pNode->pParent->nData << " ,";
411 
412         if(pNode->pLeft)
413             std::cout << "nLeftData= " << pNode->pLeft->nData << " ,";
414         if(pNode->pRight)
415             std::cout << "nRightData= " << pNode->pRight->nData << " ,";
416 
417         std::cout << "nHeight = " << pNode->nHeight << std::endl;
418     }
419     PrintTree(pNode->pLeft);
420     PrintTree(pNode->pRight);
421 }
422 #endif        //__AVLTREE_H__

  将上面的文件复制保存成文件AVLTree.h。然后将下面的复制到Test.cpp文件中。Test.cpp文件是简单的测试案例。

 1 #include "AVLTree.h"
 2 #include <iostream>
 3 #include <exception>
 4 
 5 int main()
 6 {
 7     try
 8     {
 9         AVLTree avl;
10         for(int i = 1; i < 10; i++)
11         {
12             avl.Insert(i);
13         }
14         
15         avl.Delete(4);
16         avl.Display();
17     }
18     catch (std::exception& e)
19     {
20         std::cout << e.what() << std::endl;
21     }
22 }

  输入g++ -o Test Test.cpp然后回车就可以编译运行了。运行结果如下:

 1 [kiven@localhost Test]$ g++ -o Test Test.cpp
 2 [kiven@localhost Test]$ ./Test
 3 [1]nData = 3,nParentData= 0 ,nLeftData= 2 ,nRightData= 6 ,nHeight = 3
 4 [2]nData = 2,nParentData= 3 ,nLeftData= 1 ,nHeight = 1
 5 [3]nData = 1,nParentData= 2 ,nHeight = 0
 6 [4]nData = 6,nParentData= 3 ,nLeftData= 5 ,nRightData= 8 ,nHeight = 2
 7 [5]nData = 5,nParentData= 6 ,nHeight = 0
 8 [6]nData = 8,nParentData= 6 ,nLeftData= 7 ,nRightData= 9 ,nHeight = 1
 9 [7]nData = 7,nParentData= 8 ,nHeight = 0
10 [8]nData = 9,nParentData= 8 ,nHeight = 0
11 [kiven@localhost Test]$

  我上面实现的版本也只是为了研究AVL树的属性而做的实验版本,节点中的数据也直接使用了整形,而在实际使用时需要实现模板的版本,或者用万能的指针。但是指针的方式显然没有模板好。我自己也实现了一个模板的版本,也是比较粗糙的,代码如下:

  1 #ifndef        __AVLTREE_H__
  2 #define        __AVLTREE_H__
  3 
  4 #include <iostream>
  5 
  6 template <typename T>
  7 class AVLNode
  8 {
  9 public:
 10     T data;
 11     AVLNode<T>* pLeft;
 12     AVLNode<T>* pRight;
 13     AVLNode<T>* pParent;
 14     int nHeight;
 15 };
 16 
 17 template <typename T>
 18 class AVLTree
 19 {
 20 public:
 21     AVLTree() : pRoot(NULL), nNodeCount(0){}
 22     virtual ~AVLTree(){ DeleteTree(&pRoot); }
 23 public:
 24     virtual AVLTree<T>& Insert(T data);
 25     virtual AVLTree<T>& Delete(T data);
 26     virtual int Find(T data) const;
 27     virtual int GetNodeCount() const;
 28     virtual void Display() const;
 29 
 30 private:
 31     int Max(int a, int b) const;
 32     int Height(const AVLNode<T>* pNode) const;
 33     AVLNode<T>* CreateNode(T data);
 34     AVLNode<T>* DeleteNode(T data, AVLNode<T>* pNode);
 35     AVLNode<T>* BalanceAdjust(AVLNode<T>* pNode);
 36     AVLNode<T>* RotateLeft(AVLNode<T>* pNode);
 37     AVLNode<T>* RotateRight(AVLNode<T>* pNode);
 38     AVLNode<T>* RotateLeftRight(AVLNode<T>* pNode);
 39     AVLNode<T>* RotateRightLeft(AVLNode<T>* pNode);
 40     void DeleteTree(AVLNode<T>** ppRoot);
 41     void PrintTree(AVLNode<T>* pNode) const;
 42 
 43     AVLTree(const AVLTree<T>&) {}
 44     AVLTree<T>& operator=(const AVLTree<T>&) {}
 45 
 46 private:
 47     AVLNode<T>* pRoot;
 48     int nNodeCount;
 49 };
 50 
 51 template <typename T>
 52 int AVLTree<T>::Max(int a, int b) const
 53 {
 54     return (a > b ? a : b);
 55 }
 56 
 57 template <typename T>
 58 int AVLTree<T>::Height(const AVLNode<T>* pNode) const
 59 {
 60     if (NULL == pNode)
 61         return -1;
 62 
 63     return pNode->nHeight;
 64 }
 65 
 66 template <typename T>
 67 AVLTree<T>& AVLTree<T>::Insert(T data)
 68 {
 69     if(pRoot == NULL)
 70     {
 71         pRoot = CreateNode(data);
 72 
 73         return *this;
 74     }
 75 
 76     AVLNode<T>* pInsertNode = pRoot;
 77 
 78     while(pInsertNode != NULL)
 79     {
 80         if(data < pInsertNode->data)
 81         {
 82             if(pInsertNode->pLeft == NULL)
 83             {
 84                 pInsertNode->pLeft = CreateNode(data);
 85                 pInsertNode->pLeft->pParent = pInsertNode;
 86 
 87                 pRoot = BalanceAdjust(pInsertNode->pLeft);
 88                 break;
 89             }
 90 
 91             pInsertNode = pInsertNode->pLeft;
 92         }
 93         else if(data > pInsertNode->data)
 94         {
 95             if(pInsertNode->pRight == NULL)
 96             {
 97                 pInsertNode->pRight = CreateNode(data);
 98                 pInsertNode->pRight->pParent = pInsertNode;
 99 
100                 pRoot = BalanceAdjust(pInsertNode->pRight);
101                 break;
102             }
103 
104             pInsertNode = pInsertNode->pRight;
105         }
106         else
107         {
108             return *this;
109         }
110     }
111 
112     return *this;
113 }
114 
115 template <typename T>
116 AVLTree<T>& AVLTree<T>::Delete(T data)
117 {
118     //std::cout << "Delete nData = " << nData << std::endl;
119     //std::cout << "pNode->nData = " << pNode->nData << std::endl;
120     //std::cout << "pPNode->nData = " << pPNode->nData << std::endl;
121 
122     AVLNode<T>* pCurNode = pRoot;
123 
124     while(pCurNode != NULL)
125     {
126         if(data > pCurNode->data)
127         {
128             pCurNode = pCurNode->pRight;
129         }
130         else if(data < pCurNode->data)
131         {
132             pCurNode = pCurNode->pLeft;
133         }
134         else
135         {
136             pRoot = DeleteNode(data, pCurNode);
137             break;
138         }
139     }
140 
141 
142     if(pCurNode == NULL)
143         std::cout << "没有找到元素 nData = " << data << std::endl;
144     //int x;
145     //std::cin >> x;
146 
147     return *this;//没有找到要删除的元素    
148 }
149 
150 template <typename T>
151 AVLNode<T>* AVLTree<T>::DeleteNode(T data, AVLNode<T>* pNode)
152 {
153     nNodeCount--;
154 
155     if(pNode->pLeft && pNode->pRight)//删除节点有左右子树
156     {
157         AVLNode<T>* pLMaxNode = pNode->pLeft;//删除节点左子树中最大的节点
158         AVLNode<T>* pLMaxPNode = pNode;//删除节点左子树中最大节点的父节点
159 
160         //将删除节点左孩子的最大节点替换删除节点,然后删除该节点
161         if(pLMaxNode->pRight == NULL)
162         {
163             pNode->data = pLMaxNode->data;
164             pNode->pLeft = pLMaxNode->pLeft;
165 
166             if(pLMaxNode->pLeft != NULL)
167                 pLMaxNode->pLeft->pParent = pNode;
168         }
169         else
170         {
171             while(pLMaxNode->pRight)
172             {
173                 pLMaxPNode = pLMaxNode;
174                 pLMaxNode = pLMaxNode->pRight;
175             }
176             pNode->data = pLMaxNode->data;
177 
178             if(pLMaxNode == pLMaxPNode->pRight)//将替换后的删除节点删除
179                 pLMaxPNode->pRight = pLMaxNode->pLeft;
180             else if(pLMaxNode == pLMaxPNode->pLeft)
181                 pLMaxPNode->pLeft = NULL;
182         }
183         
184         delete pLMaxNode;
185 
186         return BalanceAdjust(pLMaxPNode);
187     }
188     else if(pNode->pLeft)//删除节点只有左子树
189     {
190         AVLNode<T>* pLeft = pNode->pLeft;
191 
192         pNode->data = pLeft->data;
193 
194         pNode->pLeft = pLeft->pLeft;
195         if (pLeft->pLeft != NULL)
196             pLeft->pLeft->pParent = pNode;
197 
198         pNode->pRight = pLeft->pRight;
199         if (pLeft->pRight != NULL)
200             pLeft->pRight->pParent = pNode;
201         
202         delete pLeft;
203 
204         return BalanceAdjust(pNode);
205     }
206     else if(pNode->pRight)//删除节点只有右子树
207     {
208         AVLNode<T>* pRight = pNode->pRight;
209 
210         pNode->data = pRight->data;
211 
212         pNode->pLeft = pRight->pLeft;
213         if (pRight->pLeft != NULL)
214             pRight->pLeft->pParent = pNode;
215 
216         pNode->pRight = pRight->pRight;
217         if (pRight->pRight != NULL)
218             pRight->pRight->pParent = pNode;
219         
220         delete pRight;
221 
222         return BalanceAdjust(pNode);
223     }
224     else//删除节点没有子树
225     {
226         AVLNode<T>* pPNode = pNode->pParent;
227 
228         if(pPNode->pLeft == pNode)
229             pPNode->pLeft = NULL;
230         else if(pPNode->pRight == pNode)
231             pPNode->pRight = NULL;
232 
233         delete pNode;
234 
235         return BalanceAdjust(pPNode);
236     }
237 }
238 
239 template <typename T>
240 AVLNode<T>* AVLTree<T>::BalanceAdjust(AVLNode<T>* pNode)
241 {
242     AVLNode<T>* pRoot;
243     AVLNode<T>* pPNode;
244     
245     while(pNode != NULL)//删除节点的子节点进行平衡
246     {
247         pPNode = pNode->pParent;
248 
249         bool bIsLeft = false;
250         if(pPNode != NULL && pNode == pPNode->pLeft)
251             bIsLeft = true;
252 
253         pNode->nHeight = Max(Height(pNode->pLeft), Height(pNode->pRight)) + 1;
254 
255         if (Height(pNode->pLeft) - Height(pNode->pRight) == 2)    // AVL树不平衡  执行LL型或者LR型旋转
256         {
257             if (Height(pNode->pLeft->pLeft) - Height(pNode->pLeft->pRight) == -1)
258                 pNode = RotateLeftRight(pNode);
259             else 
260                 pNode = RotateLeft(pNode);
261 
262             if(pPNode != NULL && bIsLeft)
263                 pPNode->pLeft = pNode;
264             else if(pPNode != NULL)
265                 pPNode->pRight = pNode;
266         }
267         else if(Height(pNode->pLeft) - Height(pNode->pRight) == -2)    // AVL树不平衡  执行RR型或者RL型旋转
268         {
269             if (Height(pNode->pRight->pLeft) - Height(pNode->pRight->pRight) == 1)
270                 pNode = RotateRightLeft(pNode);
271             else
272                 pNode = RotateRight(pNode);
273 
274             if (pPNode != NULL && bIsLeft)
275                 pPNode->pLeft = pNode;
276             else if(pPNode != NULL)
277                 pPNode->pRight = pNode;
278         }
279 
280         pRoot = pNode;
281         pNode = pPNode;
282     }
283 
284     return pRoot;
285 }
286 
287 template <typename T>
288 AVLNode<T>* AVLTree<T>::CreateNode(T data)
289 {
290     nNodeCount++;
291 
292     AVLNode<T>* pNewNode = new AVLNode<T>();
293     pNewNode->data = data;
294     pNewNode->nHeight = 0;
295     pNewNode->pLeft = pNewNode->pRight = NULL;
296 
297     return pNewNode;
298 }
299 
300 template <typename T>
301 int AVLTree<T>::Find(T data) const
302 {
303     AVLNode<T>* pFindNode = pRoot;
304     while(pFindNode)
305     {
306         if(data < pFindNode->data)
307             pFindNode = pFindNode->pLeft;
308         else if(data > pFindNode->data)
309             pFindNode = pFindNode->pRight;
310         else
311             return 1;//pFindNode->data;
312     }
313     
314     return 0;
315 }
316 
317 template <typename T>
318 AVLNode<T>* AVLTree<T>::RotateLeft(AVLNode<T>* pNode)//左单
319 {
320     AVLNode<T>* pLeftChild;
321 
322     pLeftChild = pNode->pLeft;
323     pNode->pLeft = pLeftChild->pRight;
324     pLeftChild->pRight = pNode;
325 
326     pLeftChild->pParent = pNode->pParent;
327     pNode->pParent = pLeftChild;
328 
329     if(pNode->pLeft)
330         pNode->pLeft->pParent = pNode;
331 
332     // 结点的位置改变,节点高度要重新计算
333     pNode->nHeight = Max(Height(pNode->pLeft), Height(pNode->pRight)) + 1;
334     pLeftChild->nHeight = Max(Height(pLeftChild->pLeft), pNode->nHeight) + 1;
335 
336     return pLeftChild;
337 }
338 
339 template <typename T>
340 AVLNode<T>* AVLTree<T>::RotateRight(AVLNode<T>* pNode)//右单
341 {
342     AVLNode<T>* pRightChild;
343 
344     pRightChild = pNode->pRight;
345     pNode->pRight = pRightChild->pLeft;
346     pRightChild->pLeft = pNode;
347 
348     pRightChild->pParent = pNode->pParent;
349     pNode->pParent = pRightChild;
350 
351     if(pNode->pRight)
352         pNode->pRight->pParent = pNode;
353 
354     // 结点的位置改变,节点高度要重新计算
355     pNode->nHeight = Max(Height(pNode->pLeft), Height(pNode->pRight)) + 1;
356     pRightChild->nHeight = Max(Height(pRightChild->pRight), pNode->nHeight) + 1;
357 
358     return pRightChild;
359 }
360 
361 template <typename T>
362 AVLNode<T>* AVLTree<T>::RotateLeftRight(AVLNode<T>* pNode)//左双
363 {
364     pNode->pLeft = RotateRight(pNode->pLeft);
365 
366     return RotateLeft(pNode);
367 }
368 
369 template <typename T>
370 AVLNode<T>* AVLTree<T>::RotateRightLeft(AVLNode<T>* pNode)//右双
371 {
372     pNode->pRight = RotateLeft(pNode->pRight);
373 
374     return RotateRight(pNode);
375 }
376 
377 // 后序遍历树以删除树
378 template <typename T>
379 void AVLTree<T>::DeleteTree(AVLNode<T>** ppRoot)
380 {
381     if (NULL == ppRoot || NULL == *ppRoot)
382         return;
383 
384     DeleteTree(&((*ppRoot)->pLeft));
385     DeleteTree(&((*ppRoot)->pRight));
386     delete ppRoot;
387     *ppRoot = NULL;
388 
389     //std::cout << "AVLTree delete completed !" << std::endl;
390 }
391 
392 template <typename T>
393 int AVLTree<T>::GetNodeCount() const
394 {
395     return nNodeCount;
396 }
397 
398 template <typename T>
399 void AVLTree<T>::Display() const
400 {
401      PrintTree(this->pRoot);
402 }
403 
404 template <typename T>
405 void AVLTree<T>::PrintTree(AVLNode<T>* pNode) const
406 {
407     if (NULL == pRoot)
408         return;
409 
410     if (NULL == pNode)
411     {
412         return;
413     }
414 
415     static int n = 0;
416     
417     if(pNode == pRoot)
418     {
419         std::cout << "[" << ++n << "]nData = " << pNode->data << ",nParentData= 0 ,";
420 
421         if(pNode->pLeft)
422             std::cout << "nLeftData= " << pNode->pLeft->data << " ,";
423         if(pNode->pRight)
424             std::cout << "nRightData= " << pNode->pRight->data << " ,";
425 
426         std::cout << "nHeight = " << pNode->nHeight << std::endl;
427     }
428     else
429     {
430         std::cout << "[" << ++n << "]nData = " << pNode->data << ",nParentData= " << pNode->pParent->data << " ,";
431 
432         if(pNode->pLeft)
433             std::cout << "nLeftData= " << pNode->pLeft->data << " ,";
434         if(pNode->pRight)
435             std::cout << "nRightData= " << pNode->pRight->data << " ,";
436 
437         std::cout << "nHeight = " << pNode->nHeight << std::endl;
438     }
439     PrintTree(pNode->pLeft);
440     PrintTree(pNode->pRight);
441 }
442 #endif    //__AVLTREE_H__

  PS:编译和测试的方式与上面不是模板的版本一样。AVL Tree是我刚学C++不久的时候写的,存在问题在所难免。现在已经没有时间来进一步研究这个代码,放在这里做个备份,说不定什么时候就能用到呢。

    原文作者:kiven.li
    原文地址: https://www.cnblogs.com/kiven-code/archive/2013/03/01/2938651.html
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞