数据结构,堆的学习

来源:互联网 发布:gta5精简优化版 编辑:程序博客网 时间:2024/05/16 01:28

在数据结构里,堆可以实现优先队列。

优先队列(priority queue)是0个或多个元素的集合,每个元素都有一个优先权或值,对优先队列执行的操作有1) 查找;2) 插入一个新元素;3) 删除。在最小优先队列中,查找操作用来搜索优先权最小的元素,删除操作用来删除该元素;对于最大优先队列(max priority queue),查找操作用来搜索优先权最大的元素,删除操作用来删除该元素。优先权队列中的元素可以有相同的优先权,查找与删除操作可根据任意优先权进行。


抽象数据类型M a x P r i o r i t y Q u e u e{
实例
有限的元素集合,每个元素都有一个优先权
操作
C reate ( ):创建一个空的优先队列
Size ( ):返回队列中的元素数目
Max ( ):返回具有最大优先权的元素

I n s e rt (x):将x 插入队列
DeleteMax (x):从队列中删除具有最大优先权的元素,并将该元素返回至x
}



定义:[最大树(最小树)] 每个节点的值都大于(小于)或等于其子节点(如果有的话)值的树。

最大树(max tree)与最小树( min tree)的例子分别如图9 - 1、9 - 2所示,虽然这些树都是二叉树,但最大树不必是二叉树,最大树或最小树节点的子节点个数可以大于2。





定义:[最大堆(最小堆)] 最大(最小)的完全二叉树。

图9-1b 所示的最大树并不是最大堆( max heap),另外两个最大树是最大堆。图9-2b 所示的最小树不是最小堆(min heap),而另外两个是。


贴代码:

//定义堆
typedef char Element;
typedef struct BiTNode
{
int MaxSize;
int CurrentSize;
Element *heap;
}BiTNode,*BiTree;


void createHeap(BiTree &T,int maxsize)
{
T.MaxSize = maxsize;
T.heap = (Element*)malloc(sizeof(BiTNode)*maxsize+1);
T.CurrentSize = 0;
}
//插入操作


void insert(BiTree &T, const Element x)
{
//先判断堆是不是满
if(T.CurrentSize == T.MaxSize)
{
printf("堆空间满\n");
return;
}
int i = ++T.CurrentSize;
while( i != 1 && x > T.heap[i/2])
{
/**
* 如果x > T.heap[i/2],说明插入增加的节点的
*     父节点是小于x的,按照最大堆的规则,x要
*     在这个父节点之上,所以要把父节点下移到
*     增加的节点的位置。
*/
T.heap[i] = T.heap[i/2];
//把插入节点定位到父节点移动后的空出了位置
i = i/2;
}
T.heap[i] = x;
}


//删除最大堆的最大值


void DelMaxHeap(BiTree &T, Element E)
{
//判读堆是不是为空
if(0 == T.CurrentSize)
{
printf("堆为空,不能删除元素\n");
return;
}
//取出最大值
E = T.heap[1];
Element y = T.heap[T.CurrentSize];
CurrentSize--;
int i = 1;//当前空缺位置
int maxChild = 2;//记录当前空缺的孩子的最大元素的索引
while(maxChild <= T.CurrentSize)
{
//先找到i的最大孩子
if(maxChild < T.CurrentSize
  && T.heap[maxChild] < T.heap[maxChild+1])
  maxChild++;
//判断y能不能放入
//1、能
if(y >= T.heap[i])
break;
   //2、不能
//将孩子节点上移,空缺出孩子的节点最为下一次
//判断y能不能放入.
T.heap[i] = T.heap[maxChild];
i = maxChild;
maxChild *=2; 
}
T.heap[i] = y;
}












/**
* 自己背写的
*/




//最大堆的插入


void MaxHeapInsert(BiTree &T , Element E)
{
if(T.CurrentSize == T.MaxSize)
{
printf("堆空间满\n");
return;
}
int i = ++T.CurrentSize;
while(1 != i && E > T.heap[i/2])
{
T.heap[i] = T.heap[i/2];
i = i/2;
}
T.heap[i] = E;
}


//最大堆的删除最大值
void DelMaxHeap(BiTree &T, Element E)
{
if(0 == T.CurrentSize)
{
printf("堆为空,不能删除元素\n");
return;
}
E = T.heap[1];
Element y = T.heap[T.CurrentSize];
T.CurrentSize--;
int i = 1;
int maxChild = 2;
while(maxChild <= T.CurrentSize)
{
if( maxChild<T.CurrentSize && T.heap[maxChild] < T.heap[maxChild+1])
maxChild++;
if(y >= T.heap[maxChild])
break;
T.heap[i] = T.heap[maxChild];
i = maxChild;
maxChild *= 2;
}
T.heap[i] = y;
}

1 0