【0】README

0.1)为什么有这篇文章?因为 Dijkstra算法的优先队列实现 涉及到了一种新的数据结构,即优先队列(二叉堆)的操作需要更改以适应这种新的数据结构,我们暂且吧它定义为Distance, 而不是单纯的int类型;

0.2)本文源代码均为原创, int类型的优先队列(二叉堆)的操作实现,参见http://blog.csdn.net/PacosonSWJTU/article/details/49498255, (并比较他们的打印结果,很有必要)


【1】因为 Dijkstra算法的优先队列实现, 需要用到二叉堆的相关操作,但是操作的元素类型(ElementType 不是 单纯的int类型), 而是如下:

struct Distance
{
int vertexIndex; //当前顶点下标
int distance; //初始顶点到当前顶点的distance
};

【2】看个荔枝

2.1)需要特别说明的是: indexOfVertexInHeap 数组记录的是顶点vertex在 heap中的位置, 如 indexOfVertexInHeap [1] = 4;表明heap的第4个位置记录这 编号为1的vertex;

2.2)优先队列的insert和deleteMin 的执行演示(请将我的手动演示结果同我的代码打印结果做对比,经过对比,你发现它们的效果是一致的,恰好说明了我的代码的可行性):



Attention)

  • A1)其实本文中的二叉堆优先队列的实现源代码和 int类型的优先队列源代码类似,只不过它们操作的数据类型不一样罢了,当然, 这只需要简单的修改即可;
  • A2)打印结果在文末,可以看到,ElementType采用int 和 Distance的打印效果一样,这正证明了我们采用Distance结构体对源码的修改是无误的,相比于单纯的int 类型,只不过Distance又多了一个 顶点下标vertexIndex成员变量而已;

【3】source code + printing results

3.1)download source code:

https://github.com/pacosonTang/dataStructure-algorithmAnalysis/tree/master/chapter9/binaryHeap_dijkstra_prim

3.2)source code at a glance:(for complete code , please click the given link above)

1st file:distance.h

#include <stdio.h>

#define Error(str) printf("\n error: %s \n",str)   

struct Distance;
typedef struct Distance *Distance;
struct Distance
{
int vertexIndex;
int distance;
}; Distance makeEmptyDistance();

2nd file:distance.c

#include "distance.h"
#include <malloc.h> // allocate the memory for Distance struct
Distance makeEmptyDistance()
{
Distance element; element = (Distance)malloc(sizeof(struct Distance));
if(!element)
{
Error("out of space ,from func makeEmptyDistance");
return NULL;
} return element;
}

3rd file:binaryheap.h

#include <stdio.h>
#include <malloc.h>
#include "distance.h" #define ElementType Distance #define Error(str) printf("\n error: %s \n",str) struct BinaryHeap;
typedef struct BinaryHeap *BinaryHeap; void swap(ElementType x, ElementType y);
BinaryHeap initBinaryHeap(int capacity);
void insert(ElementType value, BinaryHeap bh, int*);
ElementType deleteMin(BinaryHeap, int*);
int isFull(BinaryHeap bh);
int isEmpty(BinaryHeap bh);
void percolateUp(int index, BinaryHeap bh);
void percolateDownFromOne(int index, BinaryHeap bh, int*);
void printBinaryHeap(BinaryHeap bh);
void printBinaryHeapFromZero(BinaryHeap bh); struct BinaryHeap
{
int capacity;
int size;
ElementType *elements;
};

4th file:binaryheap.c

#include "binaryheap.h"
#include <math.h> #define MaxInt (int)pow(2, 16)
//judge whether the BinaryHeap is full or not , also 1 or 0
int isFull(BinaryHeap bh)
{
return bh->size == bh->capacity - 1;
} //judge whether the BinaryHeap is empty or not , also 1 or 0
int isEmpty(BinaryHeap bh)
{
return bh->size == 0;
} // get the left child of node under index with startup 1
int leftChildFromOne(int index)
{
return index * 2;
} void printBinaryHeap(BinaryHeap bh)
{
int i;
ElementType *temp; if(!bh)
Error("printing execution failure, for binary heap is null, from func printBinaryHeap"); temp = bh->elements;
for(i = 1; i < bh->capacity; i++)
{
printf("\n\t heap[%d] = ", i);
if(i <= bh->size)
printf("vertex[%d] + distance[%d]", bh->elements[i]->vertexIndex+1, bh->elements[i]->distance);
else
printf("NULL");
}
printf("\n");
} //print the binary heap who starts from index 0
void printBinaryHeapFromZero(BinaryHeap bh)
{
int i;
ElementType *temp; if(!bh)
Error("printing execution failure, for binary heap is null, from func printBinaryHeap"); temp = bh->elements;
for(i = 0; i < bh->capacity; i++)
{
printf("\n\t index[%d] = ", i);
if(i < bh->size)
printf("%d", bh->elements[i]->distance);
else
printf("NULL");
}
printf("\n");
} void swap(ElementType x, ElementType y)
{
struct Distance temp; temp = *x;
*x = *y;
*y = temp;
} ElementType deleteMin(BinaryHeap bh, int* heapIndexRecord)
{
ElementType minimum;
ElementType *data; if(isEmpty(bh))
{
Error("failed deleting minimum , for the BinaryHeap is empty, from func deleteMin !");
return NULL;
} data = bh->elements;
minimum = data[1]; swap(data[1], data[bh->size]);
bh->size-- ; // size-- occurs prior to percolateDownFromOne
percolateDownFromOne(1, bh, heapIndexRecord) ;
return minimum;
} // percolating down the element when its value is greater than children (minimal heap)
//Attention: all of bh->elements starts from index 1
void percolateDownFromOne(int index, BinaryHeap bh, int* heapIndexRecord)
{
ElementType *data;
int size;
struct Distance temp;
int child; data = bh->elements;
size = bh->size; for(temp = *data[index]; leftChildFromOne(index) <= size; index = child)
{
child = leftChildFromOne(index);
if(child < size && data[child]->distance > data[child+1]->distance)
child++;
if(temp.distance > data[child]->distance)
{
*data[index] = *data[child];
heapIndexRecord[bh->elements[index]->vertexIndex] = index; //update the heapIndexRecord
}
else
break;
}
*data[index] = temp;
heapIndexRecord[bh->elements[index]->vertexIndex] = index; //update the heapIndexRecord
} // Attention, the index of the heap starts from 1
// return the index the element inserted into the binary heap
void insert(ElementType value, BinaryHeap bh, int* heapIndexRecord)
{
int i; if(isFull(bh))
{
Error("failed insertion , for the BinaryHeap is full, from func insert!");
return ;
}
if(!isEmpty(bh))
for(i = ++bh->size; bh->elements[i/2]->distance > value->distance; i /= 2)
{
//copyElement(bh->elements[i/2], bh->elements[i]);
*bh->elements[i] = *bh->elements[i/2];
heapIndexRecord[bh->elements[i]->vertexIndex] = i; //update the heapIndexRecord
}
else
i = ++bh->size;
*bh->elements[i] = *value;
heapIndexRecord[bh->elements[i]->vertexIndex] = i; //update the heapIndexRecord
} BinaryHeap initBinaryHeap(int capacity)
{
BinaryHeap bh;
ElementType *temp;
int i; bh = (BinaryHeap)malloc(sizeof(struct BinaryHeap));
if(!bh) {
Error("out of space, from func initBinaryHeap");
return NULL;
}
bh->capacity = capacity;
bh->size = 0; temp = (ElementType*)malloc(capacity * sizeof(Distance));
if(!temp) {
Error("out of space, from func initBinaryHeap");
return NULL;
}
bh->elements = temp; for(i=0; i < capacity; i++)
{
temp[i] = (ElementType)malloc(sizeof(struct Distance));
if(!temp[i]) {
Error("out of space, from func initBinaryHeap");
return NULL;
}
} return bh;
} // allocate the memory for storing index of vertex in heap and let every element -1
int *makeEmptyArray(int size)
{
int *array;
int i; array = (int*)malloc(size * sizeof(int));
if(!array)
{
Error("out of space ,from func makeEmptyArray");
return NULL;
}
for(i=0; i<size; i++)
array[i] = -1; return array;
} void printIndexOfVertexInHeap(int size, int *array)
{
int i; for(i=0; i<size; i++)
printf("\tindexOfVertexInHeap[%d] = %d\n", i+1, array[i]);
} int main()
{
int data[] = {85, 80, 40, 30, 10, 70, 110}; // P141
int buildHeapData[] = {150, 80, 40, 30, 10, 70, 110, 100, 20, 90, 60, 50, 120, 140, 130};
BinaryHeap bh;
int size;
int i;
int capacity;
Distance tempDisStruct;
int *indexOfVertexInHeap; printf("\n\t=== test for inserting the binary heap with {85, 80, 40, 30, 10, 70, 110} in turn ===\n");
capacity = 14;
bh = initBinaryHeap(capacity);
size = 7; tempDisStruct = makeEmptyDistance();
indexOfVertexInHeap = makeEmptyArray(size); for(i = 0; i < size; i++)
{
tempDisStruct->distance = data[i];
tempDisStruct->vertexIndex = i;
insert(tempDisStruct, bh, indexOfVertexInHeap);
}
printBinaryHeap(bh);
printIndexOfVertexInHeap(bh->size, indexOfVertexInHeap); printf("\n\t=== test for inserting the binary heap with element {100, 20, 90} in turn ===\n"); tempDisStruct->distance = 100;
tempDisStruct->vertexIndex = size;
insert(tempDisStruct, bh, indexOfVertexInHeap);
printBinaryHeap(bh); tempDisStruct->distance = 20;
tempDisStruct->vertexIndex = size+1;
insert(tempDisStruct, bh, indexOfVertexInHeap);
printBinaryHeap(bh); tempDisStruct->distance = 90;
tempDisStruct->vertexIndex = size+2;
insert(tempDisStruct, bh, indexOfVertexInHeap);
printBinaryHeap(bh); printIndexOfVertexInHeap(bh->size, indexOfVertexInHeap); printf("\n\t=== test for inserting the binary heap with 5 ===\n");
tempDisStruct->distance = 5;
tempDisStruct->vertexIndex = size+3;
insert(tempDisStruct, bh, indexOfVertexInHeap);
printBinaryHeap(bh); printf("\n\t=== test for 3 deletings towards the minimum in binary heap ===\n");
deleteMin(bh, indexOfVertexInHeap);
printBinaryHeap(bh);
deleteMin(bh, indexOfVertexInHeap);
printBinaryHeap(bh);
deleteMin(bh, indexOfVertexInHeap);
printBinaryHeap(bh);
}

3.3)printing results:





图论——Dijkstra+prim算法涉及到的优先队列(二叉堆)的更多相关文章

  1. POJ 3635 - Full Tank? - [最短路变形][手写二叉堆优化Dijkstra][配对堆优化Dijkstra]

    题目链接:http://poj.org/problem?id=3635 题意题解等均参考:POJ 3635 - Full Tank? - [最短路变形][优先队列优化Dijkstra]. 一些口胡: ...

  2. PriorityBlockingQueue优先队列的二叉堆实现

    转载请注明原创地址http://www.cnblogs.com/dongxiao-yang/p/6293807.html java.util.concurrent.PriorityBlockingQu ...

  3. 【数据结构与算法Python版学习笔记】树——利用二叉堆实现优先级队列

    概念 队列有一个重要的变体,叫作优先级队列. 和队列一样,优先级队列从头部移除元素,不过元素的逻辑顺序是由优先级决定的. 优先级最高的元素在最前,优先级最低的元素在最后. 实现优先级队列的经典方法是使 ...

  4. 最短路径——Dijkstra算法以及二叉堆优化(含证明)

    一般最短路径算法习惯性的分为两种:单源最短路径算法和全顶点之间最短路径.前者是计算出从一个点出发,到达所有其余可到达顶点的距离.后者是计算出图中所有点之间的路径距离. 单源最短路径 Dijkstra算 ...

  5. 《Algorithms算法》笔记:优先队列(2)——二叉堆

    二叉堆 1 二叉堆的定义 堆是一个完全二叉树结构(除了最底下一层,其他层全是完全平衡的),如果每个结点都大于它的两个孩子,那么这个堆是有序的. 二叉堆是一组能够用堆有序的完全二叉树排序的元素,并在数组 ...

  6. 数据结构与算法——优先队列类的C++实现(二叉堆)

    优先队列简单介绍: 操作系统表明上看着是支持多个应用程序同一时候执行.其实是每一个时刻仅仅能有一个进程执行,操作系统会调度不同的进程去执行. 每一个进程都仅仅能执行一个固定的时间,当超过了该时间.操作 ...

  7. 【算法与数据结构】二叉堆和优先队列 Priority Queue

    优先队列的特点 普通队列遵守先进先出(FIFO)的规则,而优先队列虽然也叫队列,规则有所不同: 最大优先队列:优先级最高的元素先出队 最小优先队列:优先级最低的元素先出队 优先队列可以用下面几种数据结 ...

  8. 优先队列之二叉堆与d-堆

    二叉堆简介 平时所说的堆,若没加任何修饰,一般就是指二叉堆.同二叉树一样,堆也有两个性质,即结构性和堆序性.正如AVL树一样,对堆的以此操作可能破坏者两个性质中的一个,因此,堆的操作必须要到堆的所有性 ...

  9. 纯数据结构Java实现(6/11)(二叉堆&优先队列)

    堆其实也是树结构(或者说基于树结构),一般可以用堆实现优先队列. 二叉堆 堆可以用于实现其他高层数据结构,比如优先队列 而要实现一个堆,可以借助二叉树,其实现称为: 二叉堆 (使用二叉树表示的堆). ...

随机推荐

  1. easyui combogrid 按需加载,点击下拉加载

    功能优点:减少不必要的http请求,减少服务器查询压力,降低额外的浏览器渲染,提高呈现速度开发分享: combogrid 点击才请求的功能实现简要:我分析了费用系统,和现在全网的写法.并不满意.都是要 ...

  2. Linux内核分析 - 网络

    http://blog.csdn.net/column/details/network-kernel-yoyo.html

  3. 使用canvas制作的移动端color picker

    使用canvas制作的移动端color picker 项目演示地址(用手机或者手机模式打开) 我在另一个中demo,需要用到color picker,但是找不到我需要的移动端color picker, ...

  4. [置顶] kubernetes资源类型--deployment

    Deployment(中文意思为部署.调度)提供了一种更加简单的更新RC和Pod的机制,K8S版本1.2实现的.通过在Deployment中描述所期望的集群状态,Deployment Controll ...

  5. 关于各浏览器的cookie上限

    IE6~IE6以下,每个域名最多20个cookie IE7及以上,每个域名最多50个cookie Firefox,每个域名最多50个cookie Opera,每个域名最多30个cookie Safar ...

  6. Python 面向对象一(转载)

    一.前言 1.面向对象是一种编程方式,此编程方式的实现是基于对 类 和 对象 的使用 2.类 是一个模板,模板中包装了多个“函数”供使用(可以讲多函数中公用的变量封装到对象中) 3.对象,根据模板创建 ...

  7. VirtualBox下Linux(centos)扩展磁盘空间

    最近在Linux里做文件合并,做分词,磁盘空间不够,把扩展磁盘空间方法记录一下. 1.在VirtualBox安装路径下(例如C:\Program Files\Oracle\VirtualBox> ...

  8. scss使用后的简单入门总结

    端午节第一天 将之前做的一个小demo的css样式改为了scss 好吧 改完了 赶紧由小兵 升级到中尉了 什么是scss? 我的理解是scss 就是css 的预处理器,使css变得更加富有逻辑. 有什 ...

  9. 倍福TwinCAT(贝福Beckhoff)基础教程6.1 TwinCAT如何与高级语言通讯

    因为使用TwinCAT的人用途不同,重视点就不同.如果用来代替传统PLC+HMI做项目的,很少会需要用到跟高级语言通讯,但是如果是用来做运动控制平台如做机器人运动控制器的,就肯定会用到.不管是否用得上 ...

  10. 系统重装 Windows_VHD_辅助处理工具说明文档1

    菜鸟也玩 VHD Windows VHD 辅助处理工具是一个用于创建.安装.维护 VHD 的辅助工具,把一个比较复杂的操作过程傻瓜化,使您轻松体验 VHD 的强大功能.您需要预备的就是一个准备装入 V ...