二项队列 (优先队列)~

#include<stdlib.h>
#include<stdio.h>
#define ElementType int
#define MaxSize 10
#define EdgeMin 100000000  //方便找 最小min
int Capacity = MaxSize;
typedef struct BinNode *Position;
typedef Position BinTree;
typedef struct Collection *BinQueue;
struct BinNode{
	ElementType Element;
	Position LeftChild;
	Position NextSibling;
};
struct Collection{
	int CurrentSize;
	BinTree TheTrees[MaxSize];//定义 指针数组大小 
};
BinQueue Initialize();
int IsEmpty(BinQueue H);
int IsFull(BinQueue H);
void Insert(BinQueue H);
int FindMin(BinQueue H);
BinTree CombineTrees(BinTree T1, BinTree T2);
BinQueue Merge(BinQueue H1, BinQueue H2);
ElementType DeleteMin(BinQueue H);
//void Create(BinQueue H);
int main()
	{
		BinQueue H1, H2;
		H1 = Initialize();
		H2 = Initialize();
		return 0;	
	} 
BinQueue Initialize()
	{
		int i; 
		BinQueue H = (BinQueue)malloc(sizeof(struct Collection));
		if(H == NULL){
			printf("Error");
			return NULL;
		}
		H->CurrentSize = 0;
		for(i = 0; i < MaxSize; i++ ){
			H->TheTrees[i]->Element = -1; 
			H->TheTrees[i]->LeftChild = NULL;// - 1 表示此高度下不存在根节点 
			H->TheTrees[i]->NextSibling = NULL;
		}	
		return H;
	}
		
int IsEmpty(BinQueue H)
	{
		return H->CurrentSize == 0;	
	}	
int IsFull(BinQueue H)
	{
		return H->CurrentSize == MaxSize;	
	}	
BinTree CombineTrees(BinTree T1, BinTree T2)
	{
		if(T1->Element > T2->Element)
			return CombineTrees(T2, T1);
		else if(T1->Element < T2->Element ){  //相等时候 不合并 
			T2->NextSibling = T1->LeftChild;
			T1->LeftChild = T2;
			return T1;
		}		
	}	
	
BinQueue Merge(BinQueue H1, BinQueue H2)
	{
		BinTree T1, T2, Carry = NULL;
		int i, j;
		
		if(H1->CurrentSize + H2->CurrentSize > Capacity){
			printf("Out of range");
			return NULL;
		}
		H1->CurrentSize += H2->CurrentSize; // 合并结果保存在H1 中
		for(i = 0, j = 1; j <= H1->CurrentSize; i++, j *= 2){
			T1 = H1->TheTrees[i];
			T2 = H2->TheTrees[i];
			switch(!!T1 + 2*!!T2 + 4*!!Carry)
				{
					case 0: // No tree;
					case 1: //only H1
						break;
					case 2://only H2
						H1->TheTrees[i] = T2;
						H2->TheTrees[i] = NULL;
						break;
					case 3:
						Carry = CombineTrees(T1, T2);
						H1->TheTrees[i] = H2->TheTrees[i] = NULL;
						break;	
					case 4:// only carry
						H1->TheTrees[i] = Carry;
						Carry = NULL;
						break;	
					case 5://H1 and Carry
						Carry = CombineTrees(T1, Carry);
						H1->TheTrees[i] = NULL;
						break;
					case 6:	
						Carry = CombineTrees(T2, Carry);
						H2->TheTrees[i] = NULL;
						break;
					case 7:
						H1->TheTrees[i] = Carry;
						Carry = CombineTrees(T1, T2);
						H2->TheTrees[i] = NULL;
						break;			
				}
		}
		return H1;
	}	

int FindMin(BinQueue H)
	{
		int i, min;
		int min_val = EdgeMin;
		if(IsEmpty(H)){
			printf("Error");
			return -1;
		}
		for(i = 0; i < MaxSize; i++ ){
			if(H->TheTrees[i]){
				if(H->TheTrees[i]->Element < min_val){
					min_val = H->TheTrees[i]->Element; //当前最小高度 对应根值 
					min = i; //最小的 根位置 
				}
			}
		}
		return min; 
	}
	
ElementType DeleteMin(BinQueue H)
	{
		int i;
		ElementType min_val;
		if(IsEmpty(H)){
			printf("Error");
			return -1;
		}
		int min;
		min = FindMin(H);
		BinTree OldTree, DeleteTree;
		BinQueue DeleteQueue;
		OldTree = H->TheTrees[min];
		min_val = OldTree->Element;
		DeleteTree = OldTree->LeftChild;
		free(OldTree);
		DeleteQueue = Initialize();
		DeleteQueue->CurrentSize = (1<<min)-1;  //1<<min 得到删除前个总的节点个数 
		for(i = min-1; i >=0; i-- ){//删除min后 最高的为 min-1 
			DeleteQueue->TheTrees[i] =DeleteTree;
			DeleteTree = DeleteTree->NextSibling;//递归的解散原来的关系 
			DeleteQueue->TheTrees[i]->NextSibling = NULL;//变成根结点了 没有兄弟了 
		}
		H->TheTrees[min] = NULL;
		//因为 可能还会有其它的小树 所以 拿总的 减去去掉当前删除的树的节点数 
		H->CurrentSize -= (DeleteQueue->CurrentSize + 1);
		Merge(H, DeleteQueue);
		
		return min_val; //返回删除的元素
	}	
void Insert(BinQueue H, ElementType X)//不用merge 的插入 元素方法	
	{
		int i;
		BinTree Carry;
		if(H->CurrentSize+1 > Capacity){
			printf("Out of range");
			return;
		}
		H->CurrentSize++;
		Carry = CreateTree();
		Carry->Element = X;
		//Carry->LeftChild = Carry->NextSibling = NULL;
		i = 0;
		while(H->TheTrees[i]){
			Carry = CombineTrees(Carry, H->TheTrees[i]);
			H->TheTrees[i++] = NULL;
		}
		H->TheTrees[i] = Carry;	
	}

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值