1. 基本概念
哈夫曼树:给定n个权值作为n个叶子节点,构造一棵二叉树,若该数的带权路径长度达到最小,这样的二叉树称为最优二叉树,也叫做哈夫曼树(Huffman Tree)。哈夫曼树是一个带权路径长度最短的树,其中权值越大的节点离根节点越近。
路径:在一棵树中,从一个节点往下可以到达的孩子或孙子节点之间的通路,称为路径。
路径长度:通路中分支的数组称为路径长度。若规定根节点的层数为1,则从根节点到第N层节点的路径长度为N-1.
节点的权:若将数中节点赋给一个某种含义的数值,则这个数值成为节点的权。
节点的带权路径长度:从根节点到该节点之间的路径长度与该节点权的乘积。
即:带权路径长度 = 路径长度 * 该节点权
树的带权路径长度:所有叶子节点的带权路径长度之和。记为WPL。
哈夫曼树:带权路径长度最小的就是哈夫曼树。即WPL最小。
示例:
wpl: 13 * 1 + 8 * 2 + 7 * 3 + 3 * 3 = 59
2. 步骤
把一个数组构建称哈夫曼树的步骤:
- 把数组从小到大进行排序,每个数据都是一个节点,每个节点都可以看成一个最简单的二叉树。
- 取出根节点权最小的两棵二叉树。
- 组成一棵新的二叉树,该树的根节点为去出的两棵二叉树的权值和。
- 将这棵新的二叉树,以根节点的权值进行大小排序。然后把这个新的二叉树的根节点放入数组中。重复1234的步骤,直到数组中只剩下一个树的时候,所有的数据都被处理。这时就得到了一棵哈夫曼树。
3. 示例代码
package HafmTree;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
public class HafumanTree {
public static void main(String[] args) {
int[] arr = {
13, 7, 8,