LZW编码的C/C++实现

发表于:2016-2-03 09:01

字体: | 上一篇 | 下一篇 | 我要投稿

 作者:yxwkaifa    来源:51Testing软件测试网采编

  LZW编码通过建立一个字符串表,用较短的代码来表示较长的字符串来实现压缩。 LZW压缩算法是Unisys的专利,有效期到2003年,所以相关算法大多也已过期。
  本代码只完毕了LZW的编码与解码算法功能,相对网上找到的非常多代码而言较为简(cai)单(bi)。了解struct && 会递归就可以,算是长处吧。
#include <stdio.h>
#include <algorithm>
#include <math.h>
#include <iostream>
#include <stdlib.h>
#include <string.h>
using namespace std;
struct Node{
int pre;//前缀单词相应码字
char c;//当前字符
}KDA[65535];
int cnt,P,Q;
char W,V;
void Init(){//前256个字典由相应ASCII码生成
for(int i = 0;i < 256; i ++){
KDA[i].pre = -1;
KDA[i].c = i;
}
cnt = 256;
P = -1;
}
void Out(int x){                            //递归输出码字相应单词,首位另存用于建立字典
if(KDA[x].pre != -1){
Out(KDA[x].pre);
}
else {
V = KDA[x].c;
}
printf("%c",KDA[x].c);
}
void Search(){
int flag = 0;
for(int i = 0;i < cnt;i ++){
if(KDA[i].pre == P && KDA[i].c == W){//字典已存在则更新前缀相应码字
P = i;
flag = 1;
}
}
if(!flag){                  //不存在则扩充字典,输出前缀相应码字并更新前缀单词
KDA[cnt].pre = P;
KDA[cnt].c = W;
printf("%03X ",P);
P = (int)W;
cnt ++;
}
}
void Research(){
Out(Q);
if(P != -1){                //假设前一位码字不为空,则将前一位相应单词作为前缀与本单词第一位合并作为新单词增加字典
KDA[cnt].pre = P;
KDA[cnt].c = V;
cnt ++;
}
}
void Compress(){<span style="white-space:pre"></span>//编码过程
Init();
freopen("LZWin.txt","r",stdin);
freopen("LZWch.txt","w",stdout);
while((W = getchar()) && W != EOF){
Search();
}
printf("%03X\n",P);
}
void Decompress(){<span style="white-space:pre"></span>//解码过程
Init();
freopen("LZWch.txt","r",stdin);
freopen("LZWout.txt","w",stdout);
while(scanf("%03X",&Q)!= EOF){
Research();
}
}
int main(){
Compress();
Decompress();
return 0;
}
《2023软件测试行业现状调查报告》独家发布~

关注51Testing

联系我们

快捷面板 站点地图 联系我们 广告服务 关于我们 站长统计 发展历程

法律顾问:上海兰迪律师事务所 项棋律师
版权所有 上海博为峰软件技术股份有限公司 Copyright©51testing.com 2003-2024
投诉及意见反馈:webmaster@51testing.com; 业务联系:service@51testing.com 021-64471599-8017

沪ICP备05003035号

沪公网安备 31010102002173号