Java数据结构与算法解析(十四)——二叉堆
Posted 4K_WarCraft
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Java数据结构与算法解析(十四)——二叉堆相关的知识,希望对你有一定的参考价值。
二叉堆概述
二叉堆是完全二元树或者是近似完全二元树,按照数据的排列方式可以分为两种:最大堆和最小堆。
最大堆:父结点的键值总是大于或等于任何一个子节点的键值;最小堆:父结点的键值总是小于或等于任何一个子节点的键值。
二叉堆一般都通过”数组”来实现,下面是数组实现的最大堆和最小堆的示意图:
二叉堆的实现
本实现以”最大堆”为例子来进行介绍。
1. 添加
假设在最大堆[90,80,70,60,40,30,20,10,50]种添加85,需要执行的步骤如下:
当向最大堆中添加数据时:先将数据加入到最大堆的最后,然后尽可能把这个元素往上挪,直到挪不动!
将85添加到[90,80,70,60,40,30,20,10,50]中后,最大堆变成了[90,85,70,60,80,30,20,10,50,40]。
最大堆的插入代码
protected void filterup(int start)
int c = start;
int p = (c-1)/2;
T tmp = mHeap.get(c);
while(c > 0)
int cmp = mHeap.get(p).compareTo(tmp);
if(cmp >= 0)
break;
else
mHeap.set(c, mHeap.get(p));
c = p;
p = (p-1)/2;
mHeap.set(c, tmp);
public void insert(T data)
int size = mHeap.size();
mHeap.add(data);
filterup(size);
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
insert(data)的作用:将数据data添加到最大堆中。mHeap是动态数组ArrayList对象。
当堆已满的时候,添加失败;否则data添加到最大堆的末尾。然后通过上调算法重新调整数组,使之重新成为最大堆。
2. 删除
假设从最大堆[90,85,70,60,80,30,20,10,50,40]中删除90,需要执行的步骤如下:
当从最大堆中删除数据时:先删除该数据,然后用最大堆中最后一个的元素插入这个空位;接着,把这个“空位”尽量往上挪,直到剩余的数据变成一个最大堆。
从[90,85,70,60,80,30,20,10,50,40]删除90之后,最大堆变成了[85,80,70,60,40,30,20,10,50]。
注意:考虑从最大堆[90,85,70,60,80,30,20,10,50,40]中删除60,执行的步骤不能单纯的用它的子节点来替换;而必须考虑到”替换后的树仍然要是最大堆”!
二叉堆的删除代码
protected void filterdown(int start, int end)
int c = start;
int l = 2*c + 1;
T tmp = mHeap.get(c);
while(l <= end)
int cmp = mHeap.get(l).compareTo(mHeap.get(l+1));
if(l < end && cmp<0)
l++;
cmp = tmp.compareTo(mHeap.get(l));
if(cmp >= 0)
break;
else
mHeap.set(c, mHeap.get(l));
c = l;
l = 2*l + 1;
mHeap.set(c, tmp);
public int remove(T data)
if(mHeap.isEmpty() == true)
return -1;
int index = mHeap.indexOf(data);
if (index==-1)
return -1;
int size = mHeap.size();
mHeap.set(index, mHeap.get(size-1));
mHeap.remove(size - 1);
if (mHeap.size() > 1)
filterdown(index, mHeap.size()-1);
return 0;
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
完整代码
二叉堆(最大堆)的实现
public class MaxHeap<T extends Comparable<T>>
private List<T> mHeap;
public MaxHeap()
this.mHeap = new ArrayList<T>();
protected void filterdown(int start, int end)
int c = start;
int l = 2*c + 1;
T tmp = mHeap.get(c);
while(l <= end)
int cmp = mHeap.get(l).compareTo(mHeap.get(l+1));
if(l < end && cmp<0)
l++;
cmp = tmp.compareTo(mHeap.get(l));
if(cmp >= 0)
break;
else
mHeap.set(c, mHeap.get(l));
c = l;
l = 2*l + 1;
mHeap.set(c, tmp);
public int remove(T data)
if(mHeap.isEmpty() == true)
return -1;
int index = mHeap.indexOf(data);
if (index==-1)
return -1;
int size = mHeap.size();
mHeap.set(index, mHeap.get(size-1));
mHeap.remove(size - 1);
if (mHeap.size() > 1)
filterdown(index, mHeap.size()-1);
return 0;
protected void filterup(int start)
int c = start;
int p = (c-1)/2;
T tmp = mHeap.get(c);
while(c > 0)
int cmp = mHeap.get(p).compareTo(tmp);
if(cmp >= 0)
break;
else
mHeap.set(c, mHeap.get(p));
c = p;
p = (p-1)/2;
mHeap.set(c, tmp);
public void insert(T data)
int size = mHeap.size();
mHeap.add(data);
filterup(size);
@Override
public String toString()
StringBuilder sb = new StringBuilder();
for (int i=0; i<mHeap.size(); i++)
sb.append(mHeap.get(i) +" ");
return sb.toString();
public static void main(String[] args)
int i;
int a[] = 10, 40, 30, 60, 90, 70, 20, 50, 80;
MaxHeap<Integer> tree=new MaxHeap<Integer>();
System.out.printf("== 依次添加: ");
for(i=0; i<a.length; i++)
System.out.printf("%d ", a[i]);
tree.insert(a[i]);
System.out.printf("\\n== 最 大 堆: %s", tree);
i=85;
tree.insert(i);
System.out.printf("\\n== 添加元素: %d", i);
System.out.printf("\\n== 最 大 堆: %s", tree);
i=90;
tree.remove(i);
System.out.printf("\\n== 删除元素: %d", i);
System.out.printf("\\n== 最 大 堆: %s", tree);
System.out.printf("\\n");
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
- 72
- 73
- 74
- 75
- 76
- 77
- 78
- 79
- 80
- 81
- 82
- 83
- 84
- 85
- 86
- 87
- 88
- 89
- 90
- 91
- 92
- 93
- 94
- 95
- 96
- 97
- 98
- 99
- 100
- 101
- 102
- 103
- 104
- 105
- 106
- 107
- 108
- 109
- 110
- 111
- 112
- 113
- 114
- 115
- 116
- 117
- 118
- 119
- 120
- 121
- 122
- 123
- 124
- 125
- 126
- 127
- 128
- 129
- 130
- 131
- 132
- 133
- 134
- 135
- 136
二叉堆(最小堆)的实现文件
public class MinHeap<T extends Comparable<T>>
private List<T> mHeap;
public MinHeap()
this.mHeap = new ArrayList<T>();
protected void filterdown(int start, int end)
int c = start;
int l = 2*c + 1;
T tmp = mHeap.get(c);
while(l <= end)
int cmp = mHeap.get(l).compareTo(mHeap.get(l+1));
if(l < end && cmp>0)
l++;
cmp = tmp.compareTo(mHeap.get(l));
if(cmp <= 0)
break;
else
mHeap.set(c, mHeap.get(l));
c = l;
l = 2*l + 1;
mHeap.set(c, tmp);
public int remove(T data)
if(mHeap.isEmpty() == true)
Java 数据结构 & 算法宁可累死自己, 也要卷死别人 13 二叉堆
Java 数据结构 & 算法宁可累死自己, 也要卷死别人 13 二叉堆
数据结构与算法 通俗易懂讲解 二叉堆实现
算法与数据结构二叉堆是什么鬼?
算法与数据结构堆排序是什么鬼?
JavaScript数据结构与算法 - 二叉堆和堆排序