C源码@数据结构与算法->BinomialQueue
2015-08-24 20:00
701 查看
/* * fatal.h */ #include #include #define Error(Str) FatalError(Str) #define FatalError(Str) fprintf(stderr, "%s\n", Str), exit(-1)
/* * testbin.cpp */ #include #include "binomial.h" #define MaxSize (12000) int main() { BinQueue H; int i, j; ElementType AnItem; H = Initialize(); for (i = 0, j = MaxSize / 2; i < MaxSize; ++i, j = (j + 71) % MaxSize) { H = Insert(j, H); } j = 0; while (!IsEmpty(H)) { if (DeleteMin(H) != j++) { printf("Error in DeleteMin, %d\n", j); } } if (j != MaxSize) { printf("Error in counting!\n"); } printf("Done...\n"); return 0; }
/* * binomial.h */ #ifndef _BINQUEUE_H #define _BINQUEUE_H #ifndef NULL #define NULL (0) #endif typedef long ElementType; #define Infinity (30000L) #define MaxTrees (14) /* Stores 2^14 - 1 items */ #define Capacity (16383) struct BinNode; typedef struct BinNode *BinTree; struct Collection; typedef struct Collection *BinQueue; #ifdef __cplusplus extern "C" { #endif BinQueue Initialize(); void Destroy(BinQueue H); BinQueue MakeEmpty(BinQueue H); BinQueue Insert(ElementType Item, BinQueue H); BinQueue Merge(BinQueue H1, BinQueue H2); int IsEmpty(BinQueue H); int IsFull(BinQueue H); ElementType FindMin(BinQueue H); ElementType DeleteMin(BinQueue H); #ifdef __cplusplus } #endif #endif /* _BINQUEUE_H */
/* * binomial.cpp */ #include #include "fatal.h" #include "binomial.h" typedef struct BinNode *Position; struct BinNode { ElementType Element; Position LeftChild; Position NextSibling; }; struct Collection { int CurrentSize; BinTree TheTrees[MaxTrees]; }; BinQueue Initialize() { BinQueue H; int i; H = (BinQueue)malloc(sizeof(struct Collection)); if (H == NULL) { FatalError("Out of space!"); } H->CurrentSize = 0; for (i = 0; i < MaxTrees; ++i) { H->TheTrees[i] = NULL; } return H; } static void DestroyTree(BinTree T) { if (T != NULL) { DestroyTree(T->LeftChild); DestroyTree(T->NextSibling); free(T); } } void Destroy(BinQueue H) { int i; for (i = 0; i < MaxTrees; ++i) { DestroyTree(H->TheTrees[i]); } } BinQueue MakeEmpty(BinQueue H) { int i; Destroy(H); for (i = 0; i < MaxTrees; ++i) { H->TheTrees[i] = NULL; } return H; } BinQueue Insert(ElementType Item, BinQueue H) { BinTree NewNode; BinQueue OneItem; NewNode = (BinTree)malloc(sizeof(struct BinNode)); if (NewNode == NULL) { FatalError("Out of space!"); } NewNode->LeftChild = NULL; NewNode->NextSibling = NULL; NewNode->Element = Item; OneItem = Initialize(); OneItem->CurrentSize = 1; OneItem->TheTrees[0] = NewNode; return Merge(H, OneItem); } BinTree CombineTrees(BinTree T1, BinTree T2) { if (T1->Element > T2->Element) { return CombineTrees(T2, T1); } 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) { FatalError("Merge would exceed capacity!"); } H1->CurrentSize += H2->CurrentSize; 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 trees */ case 1: /* Only H1 */ break; case 2: /* Only H2 */ H1->TheTrees[i] = T2; H2->TheTrees[i] = NULL; break; case 4: /* Only Carry */ H1->TheTrees[i] = Carry; Carry = NULL; break; case 3: /* H1 and H2 */ Carry = CombineTrees(T1, T2); H1->TheTrees[i] = NULL; H2->TheTrees[i] = NULL; break; case 5: /* H1 and Carry */ Carry = CombineTrees(T1, Carry); H1->TheTrees[i] = NULL; break; case 6: /* H2 and Carry */ Carry = CombineTrees(T2, Carry); H2->TheTrees[i] = NULL; break; case 7: /* All threes */ H1->TheTrees[i] = Carry; Carry = CombineTrees(T1, T2); H2->TheTrees[i] = NULL; break; } } return H1; } int IsEmpty(BinQueue H) { return H->CurrentSize == 0; } int IsFull(BinQueue H) { return H->CurrentSize == Capacity; } ElementType FindMin(BinQueue H) { int i; ElementType MinItem; if (IsEmpty(H)) { FatalError("Empty binomial queue!"); } MinItem = Infinity; for (i = 0; i < MaxTrees; ++i) { if (H->TheTrees[i] && H->TheTrees[i]->Element < MinItem) { MinItem = H->TheTrees[i]->Element < MinItem; } } return MinItem; } ElementType DeleteMin(BinQueue H) { int i, j; int MinTree; /* The tree with the minimum item */ BinQueue DeletedQueue; Position DeletedTree, OldRoot; ElementType MinItem; if (IsEmpty(H)) { FatalError("Empty binomial queue!"); } MinItem = Infinity; for (i = 0; i < MaxTrees; ++i) { if (H->TheTrees[i] && H->TheTrees[i]->Element < MinItem) { /* Update minimum */ MinItem = H->TheTrees[i]->Element; MinTree = i; } } DeletedTree = H->TheTrees[MinTree]; OldRoot = DeletedTree; DeletedTree = DeletedTree->LeftChild; free(OldRoot); DeletedQueue = Initialize(); DeletedQueue->CurrentSize = (1 << MinTree) - 1; for (j = MinTree - 1; j >= 0; j--) { DeletedQueue->TheTrees[j] = DeletedTree; DeletedTree = DeletedTree->NextSibling; DeletedQueue->TheTrees[j]->NextSibling = NULL; } H->TheTrees[MinTree] = NULL; H->CurrentSize -= DeletedQueue->CurrentSize + 1; Merge(H, DeletedQueue); return MinItem; }
相关文章推荐
- 数据结构之队列
- 数据结构与算法-大数据排序
- java数据结构之链表
- 数据结构与算法-归并排序
- 数据结构与算法-快速排序
- 数据结构与算法-插入排序
- 数据结构与算法-选择排序
- 数据结构与算法-冒泡排序
- 数据结构与算法-二叉树
- 数据结构与算法-链表
- 数据结构与算法-队列
- 数据结构与算法基础1
- java数据结构(三)排序
- 数据结构学习之路-第二章:线性表的顺序表示与实现
- java数据结构学习笔记(二)数组
- 字典树(Trie树、单词查找树、前缀树)
- 数据结构七:选择,冒泡,插入,希尔,快速排序实现
- 基本数据结构:链表
- Python数据结构:序列——元组和列表
- Android的NDK开发(4)————JNI数据结构之JNINativeMethod