易网时代-编程资源站
Welcome
微信登录
首页
/
操作系统
/
Linux
/
Java 哈夫曼编码反编码的实现
Java 哈夫曼编码反编码的实现:
//哈弗曼编码的实现类
public
class
HffmanCoding {
private
int
charsAndWeight[][];
// [][0]是 字符,[][1]存放的是字符的权值(次数)
private
int
hfmcoding[][];
// 存放哈弗曼树
private
int
i =
0
;
// 循环变量
private
String hcs[];
public
HffmanCoding(
int
[][] chars) {
// TODO 构造方法
charsAndWeight =
new
int
[chars.length][
2
];
charsAndWeight = chars;
hfmcoding =
new
int
[
2
* chars.length -
1
][
4
];
// 为哈弗曼树分配空间
}
// 哈弗曼树的实现
public
void
coding() {
int
n = charsAndWeight.length;
if
(n ==
0
)
return
;
int
m =
2
* n -
1
;
// 初始化哈弗曼树
for
(i =
0
; i < n; i++) {
hfmcoding[i][
0
] = charsAndWeight[i][
1
];
// 初始化哈弗曼树的权值
hfmcoding[i][
1
] =
0
;
// 初始化哈弗曼树的根节点
hfmcoding[i][
2
] =
0
;
// 初始化哈弗曼树的左孩子
hfmcoding[i][
3
] =
0
;
// 初始化哈弗曼树的右孩子
}
for
(i = n; i < m; i++) {
hfmcoding[i][
0
] =
0
;
// 初始化哈弗曼树的权值
hfmcoding[i][
1
] =
0
;
// 初始化哈弗曼树的根节点
hfmcoding[i][
2
] =
0
;
// 初始化哈弗曼树的左孩子
hfmcoding[i][
3
] =
0
;
// 初始化哈弗曼树的右孩子
}
// 构建哈弗曼树
for
(i = n; i < m; i++) {
int
s1[] = select(i);
// 在哈弗曼树中查找双亲为零的 weight最小的节点
hfmcoding[s1[
0
]][
1
] = i;
// 为哈弗曼树最小值付双亲
hfmcoding[s1[
1
]][
1
] = i;
hfmcoding[i][
2
] = s1[
0
];
// 新节点的左孩子
hfmcoding[i][
3
] = s1[
1
];
// 新节点的右孩子
hfmcoding[i][
0
] = hfmcoding[s1[
0
]][
0
] + hfmcoding[s1[
1
]][
0
];
// 新节点的权值是左右孩子的权值之和
}
}
// 查找双亲为零的 weight最小的节点
private
int
[] select(
int
w) {
// TODO Auto-generated method stub
int
s[] = { -
1
, -
1
}, j =
0
;
// s1 最小权值且双亲为零的节点的序号 , i 是循环变量
int
min1 =
32767
, min2 =
32767
;
for
(j =
0
; j < w; j++) {
if
(hfmcoding[j][
1
] ==
0
) {
// 只在尚未构造二叉树的结点中查找(双亲为零的节点)
if
(hfmcoding[j][
0
] < min1) {
min2 = min1;
s[
1
] = s[
0
];
min1 = hfmcoding[j][
0
];
s[
0
] = j;
}
else
if
(hfmcoding[j][
0
] < min2) {
min2 = hfmcoding[j][
0
];
s[
1
] = j;
}
}
}
return
s;
}
public
String[] CreateHCode() {
// 根据哈夫曼树求哈夫曼编码
int
n = charsAndWeight.length;
int
i, f, c;
String hcodeString =
""
;
hcs =
new
String[n];
for
(i =
0
; i < n; i++) {
// 根据哈夫曼树求哈夫曼编码
c = i;
hcodeString =
""
;
f = hfmcoding[i][
1
];
// f 哈弗曼树的根节点
while
(f !=
0
) {
// 循序直到树根结点
if
(hfmcoding[f][
2
] == c) {
// 处理左孩子结点
hcodeString +=
"0"
;
}
else
{
hcodeString +=
"1"
;
}
c = f;
f = hfmcoding[f][
1
];
}
hcs[i] =
new
String(
new
StringBuffer(hcodeString).reverse());
}
return
hcs;
}
public
String show(String s) {
// 对字符串显示编码
String textString =
""
;
char
c[];
int
k = -
1
;
c =
new
char
[s.length()];
c = s.toCharArray();
// 将字符串转化为字符数组
for
(
int
i =
0
; i < c.length; i++) {
k = c[i];
for
(
int
j =
0
; j < charsAndWeight.length; j++)
if
(k == charsAndWeight[j][
0
])
textString += hcs[j];
}
return
textString;
}
// 哈弗曼编码反编译
public
String reCoding(String s) {
String text =
""
;
// 存放反编译后的字符
int
k =
0
, m = hfmcoding.length -
1
;
// 从根节点开始查询
char
c[];
c =
new
char
[s.length()];
c = s.toCharArray();
k = m;
for
(
int
i =
0
; i < c.length; i++) {
if
(c[i] ==
"0"
) {
k = hfmcoding[k][
2
];
// k的值为根节点左孩子的序号
if
(hfmcoding[k][
2
] ==
0
&& hfmcoding[k][
3
] ==
0
)
// 判断是不是叶子节点,条件(左右孩子都为零)
{
text += (
char
) charsAndWeight[k][
0
];
k = m;
}
}
if
(c[i] ==
"1"
) {
k = hfmcoding[k][
3
];
// k的值为根节点右孩子的序号
if
(hfmcoding[k][
2
] ==
0
&& hfmcoding[k][
3
] ==
0
)
// 判断是不是叶子节点,条件(左右孩子都为零)
{
text += (
char
) charsAndWeight[k][
0
];
k = m;
}
}
}
return
text;
}
}
调用的时候直接调用该类就行了
eg :
int
chars[][] ;
String s =“
101010110
”;
HffmanCoding hfc =
new
HffmanCoding(chars);
hfc.coding();
//哈弗曼树
String s[] = hfc.CreateHCode();
//哈弗曼编码
s=hfc.show(s);
版权所有©石家庄振强科技有限公司2024
冀ICP备08103738号-5
网站地图