堆的基本操作:定义、创建、插入、删除、排序
2015-06-04 15:38
323 查看
#include <iostream> using namespace std; #include <cstdlib> #include <cstring> typedef int heap_elem_t; typedef struct heap_t { int size; /** 实际元素个数*/ int capacity; /** 容量,以元素为单位*/ heap_elem_t *elems; /** 堆的数组*/ int (*cmp)(const heap_elem_t*, const heap_elem_t*); /** 元素的比较函数*/ }heap_t; int cmp_int(const int *x, const int *y) { const int sub = *x - *y; if(sub > 0) return 1; else if(sub < 0) return -1; else return 0; } heap_t* heap_create(const int capacity, int (*cmp)(const heap_elem_t*, const heap_elem_t*)) { heap_t *h = (heap_t*)malloc(sizeof(heap_t)); h->size = 0; h->capacity = capacity; h->elems = (heap_elem_t*)malloc(capacity * sizeof(heap_elem_t)); h->cmp = cmp; return h; } void heap_destroy(heap_t *h) { free(h->elems); free(h); } int heap_empty(const heap_t *h) { return h->size == 0; } int heap_size(const heap_t *h) { return h->size; } void heap_sift_down(const heap_t *h, const int start) { int i = start; int j; const heap_elem_t tmp = h->elems[start]; for(j = 2 * i + 1; j < h->size; j = 2 * j + 1) { if(j < (h->size - 1) && h->cmp(&(h->elems[j]), &(h->elems[j + 1])) > 0) { j++; /* j 指向两子女中小者*/ } if(h->cmp(&tmp, &(h->elems[j])) <= 0) { break; } else { h->elems[i] = h->elems[j]; i = j; } } h->elems[i] = tmp; } void heap_sift_up(const heap_t *h, const int start) { int j = start; int i= (j - 1) / 2; const heap_elem_t tmp = h->elems[start]; while(j > 0) { if(h->cmp(&(h->elems[i]), &tmp) <= 0) { break; } else { h->elems[j] = h->elems[i]; j = i; i = (i - 1) / 2; } } h->elems[j] = tmp; } void heap_push(heap_t *h, const heap_elem_t x) { if(h->size == h->capacity) /* 已满,重新分配内存*/ { heap_elem_t* tmp = (heap_elem_t*)realloc(h->elems, h->capacity * 2 * sizeof(heap_elem_t)); h->elems = tmp; h->capacity *= 2; } h->elems[h->size] = x; h->size++; heap_sift_up(h, h->size - 1); } void heap_pop(heap_t *h) { h->elems[0] = h->elems[h->size - 1]; h->size --; heap_sift_down(h, 0); } heap_elem_t heap_top(const heap_t *h) { return h->elems[0]; } <pre name="code" class="cpp">void heap_sort(heap_elem_t *a, const int n, int (*cmp)(const heap_elem_t*, const heap_elem_t*)) { int i; heap_t *h; heap_elem_t tmp; h = heap_create(n, cmp); h->elems = a; i = (h->size - 2)/2; /* 找最初调整位置:最后分支结点*/ while (i >= 0) /* 自底向上逐步扩大形成堆*/ { heap_sift_down(h, i); i--; } for (i = h->size - 1; i > 0; i--) { tmp = h->elems[i]; h->elems[i] = h->elems[0]; h->elems[0] = tmp; h->size = i; /* 相当于h.size -- */ heap_sift_down(h, 0); } heap_destroy(h); }
相关文章推荐
- BZOJ2730 矿场搭建
- 如何在安装32位Oracle客户端组件的情况下以64位模式运行
- 2015年大一下第13周项目1-小玩文件
- CCNA学习指南 网络互联
- Process.StandardOutput.ReadToEnd()卡死假象(非卡死)
- Java Exlips 操作 Hadoop
- Building a Raspberry Pi 2 WebRTC camera
- 理解SQL Server中的权限体系(下)----安全对象和权限
- navicat导入mysql数据库sql时报错
- linux 下重启mysql数据库的方法
- SVN服务器客户端以及环境的搭建和使用
- 自己写的存储过程要记住二:(一个删了好多表的存储过程)
- UVa 10118 Free Candies
- 使用ssh或者远程执行命令是的一些问题解决方法
- Centos 安装Ftp客户端和开启vsftp服务
- Linux 强制位、冒险位
- Linux服务器上设置SSH登录后发送email提醒的方法
- 期权期货及其他衍生产品
- 第三天 ThinkPHP手把手快速拼接网站(三)
- 理解SQL Server中的权限体系(上)----主体