驱动环境下c语言的AVL平衡树实现

       本文主对以前在CSDN上发表的平衡树进行改进,修正了一个bug,并且树节点数据改为void*.另外平衡树的内存管理采用了非分页的内存,应用在驱动编程中.此算法已经应用于一个map的实现,经过了测试.如果想将平衡树应用于用户模式下,可以把头文件中的_KERNAL_MODE_定义去掉,然后包含头文件 stdlib.h .如果还有bug,欢迎联系我修正 msn:felix_lzq@hotmail.com

//
///  @file  _AVLTree.h
///  @author  liuzongqiang
///  @date  2008-8-19-17:00
///
///  @brief     AVL平衡树的c语言实现,采用非分页内存
//
#ifndef ___AVLTREE___
#define ___AVLTREE___
#define  _KERNAL_MODE_

#ifdef _KERNAL_MODE_
#include "wdm.h"
#define  AVL_Allocate(size) ExAllocatePool( NonPagedPool , (size))
#define AVL_Free(paddr) ExFreePool(paddr)
#else
#define AVL_Allocate(size) malloc((size))
#define AVL_Free(paddr) free(paddr)
#endif

#ifdef __cplusplus
#define _AVL_INLENE inline
#else
#define _AVL_INLENE
#endif

typedef void* AVL_Element;
typedef ULONG AVL_Key ;
extern struct AVL_TreeNode;
typedef struct AVL_TreeNode *AVL_Tree;
typedef struct AVL_TreeNode *AVL_Position;
typedef size_t AVL_Size;

AVL_Tree AVL_MakeEmpty(AVL_Tree t);
AVL_Position AVL_Find(AVL_Key e,AVL_Tree t);
AVL_Position AVL_FindMin(AVL_Tree t);
AVL_Position AVL_FindMax(AVL_Tree t);
AVL_Tree AVL_Delete(AVL_Key e ,AVL_Tree t);
AVL_Tree AVL_Insert(AVL_Element e ,AVL_Tree t);
AVL_Element AVL_Retrieve(AVL_Position p);
AVL_Size AVL_GetSize(AVL_Tree t );

#endif

 

 

 

//
///  @file  _AVLTree.cpp
///  @author  liuzongqiang
///  @date  2008-8-19-17:00
///
///  @brief     AVL平衡树的c语言实现,采用非分页内存
//

#include "_AVLTree.h"
#define MAX(a,b) ((a>b)?a:b)

/*Assume that e is a "void *" pointer*/
#define  AVL_KEY(e) (*((ULONG*)(e)))
struct AVL_TreeNode
{
 int height;
 AVL_Element e;
 AVL_Tree left;
 AVL_Tree right;
};
static _AVL_INLENE int Height(AVL_Position p)
{
 if(p)
  return p->height;
 return -1;
}
/*rotate function*/
AVL_Position AVL_SingleRotateLeft(AVL_Position p)
{
 AVL_Position tmp;
 tmp = p->left;
 p->left = tmp->right;
 tmp->right = p;
 p->height = MAX(Height(p->left) , Height(p->right)) + 1;
 tmp->height = MAX(Height(tmp->left) , p->height);
 return tmp;

}
AVL_Position AVL_SingleRotateRight(AVL_Position p)
{
 AVL_Position tmp;
 tmp = p->right;
 p->right = tmp->left;
 tmp->left = p;
 p->height = MAX(Height(p->left) , Height(p->right))+1;
 tmp->height = MAX(p->height , Height(tmp->right));
 return tmp;
}
AVL_Position AVL_DoubleRotateRight(AVL_Position p)
{
 p->right = AVL_SingleRotateLeft(p->right);
 return AVL_SingleRotateRight(p);
}
AVL_Position AVL_DoubleRotateLeft(AVL_Position p)
{
 p->left = AVL_SingleRotateRight(p->left);
 return AVL_SingleRotateLeft(p);
}

AVL_Tree AVL_MakeEmpty(AVL_Tree t)
{
 if(t)
 {
  AVL_MakeEmpty(t->left);
  AVL_MakeEmpty(t->right);
  AVL_Free(t);
 }
 return NULL;
}
AVL_Position AVL_Find(AVL_Key key , AVL_Tree t)
{

 if(t)
 {
  if(key>AVL_KEY(t->e))
   return AVL_Find(key , t->right);
  else if(key<AVL_KEY(t->e))
   return AVL_Find(key , t->left);
  else
   return (AVL_Position)t;
 }
 else return NULL;
}

/*find the minimum element*/
AVL_Position AVL_FindMin(AVL_Tree t)
{
 if(t)
  while(t->left)
   t = t->left;
 return (AVL_Position)t;
}
/*find the maximum element*/
AVL_Position AVL_FindMax(AVL_Tree t)
{
 if(t)
  while(t->right)
   t = t->right;
 return (AVL_Position)t;
}

static AVL_Tree AVL_Rebalance(AVL_Position p)
{
 if ( NULL == p)
 {
  return NULL ;
 }
 if(Height(p->left)-Height(p->right)==2)
 {
  if(Height(p->left->left)>Height(p->left->right))/*LL**/
  {
   return AVL_SingleRotateLeft(p);
  }
  else/*LR*/
  {
   return AVL_DoubleRotateLeft(p);
  }
 }
 else
  if(Height(p->left)-Height(p->right)==-2)
  {

   if(Height(p->right->right)>Height(p->right->left))/*RR**/
   {
    return AVL_SingleRotateRight(p);
   }/*RL*/
   else
   {
    return AVL_DoubleRotateRight(p);
   }
  }
  return p;
}
static AVL_Tree AVL_DeleteMin(AVL_Tree t)
{
 if(t->left){
  t = AVL_DeleteMin(t->left);
  return AVL_Rebalance(t);
 }
 else
 {
  AVL_Free(t);
  return NULL;
 }
}
AVL_Tree AVL_Delete(AVL_Key key  , AVL_Tree t)
{
 AVL_Position p = NULL ;
 if(t)
 {
  if(key>AVL_KEY(t->e))
   t->right = AVL_Delete(key , t->right);
  else if(key<AVL_KEY(t->e))
   t->left = AVL_Delete(key , t->left);
  /*find it*/
  else if(t->left&&t->right)
  {
   p = AVL_FindMin(t->right);
   t->e = p->e;
   t->right = AVL_DeleteMin(t->right);
  }
  else
  {
   p = t;
   if(t->left==NULL)
    t = t->right;
   else
    t = t->left;
   AVL_Free(p);
  }
 }
 return AVL_Rebalance(t);
}

AVL_Tree AVL_Insert(AVL_Element e  , AVL_Tree t)
{
 ASSERT( NULL != e );

 if(t==NULL)/*insert as leaf child*/
 {
  t = (AVL_Tree)AVL_Allocate(NonPagedPool  , sizeof(struct AVL_TreeNode));
  if ( NULL == t)
   return NULL;
  t->e = e;
  t->left = t->right = NULL;
  t->height = 0;
 }
 else
  if(AVL_KEY(e)>AVL_KEY(t->e))
  {
   t->right = AVL_Insert(e , t->right);
   if(Height(t->right)-Height(t->left)==2)
   {
    if(AVL_KEY(e)>AVL_KEY(t->right->e))
     t = AVL_SingleRotateRight(t);
    else
     t = AVL_DoubleRotateRight(t);
   }
  }
  else if(AVL_KEY(e)<AVL_KEY(t->e))
  {
   t->left = AVL_Insert(e , t->left);
   if(Height(t->left)-Height(t->right)==2)
   {
    if(AVL_KEY(e)<AVL_KEY(t->left->e))
     t = AVL_SingleRotateLeft(t);
    else
     t = AVL_DoubleRotateLeft(t);
   }
  }
  else
  {
   t->e = e;
  }
 t->height = MAX(Height(t->left) , Height(t->right))+1;
 return t;
}

 AVL_Element AVL_Retrieve(AVL_Position p)
{
 ASSERT( NULL != p ) ;
 return p->e;
}


 AVL_Size AVL_GetSize(AVL_Tree t )
 {

  if ( NULL == t )
  {
   return 0 ;
  }
  return AVL_GetSize(t->left) + AVL_GetSize(t->right) + 1;

 }

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值