一 目的
利用C/C++语言进行程序设计,巩固和加深对线性表、栈、队列、字符串、树、图、查找、排序等理论知识的理解;掌握现实复杂问题的分析建模和解决方法(包括问题描述、系统分析、设计建模、代码实现、结果分析等);加深对哈夫曼树实现算法的理解。和. 加深对二叉树遍历算法的理解,提高利用计算机分析解决综合性实际问题的基本能力。
二 需求分析
1 知识点:
链表的创建,链表排序,二叉树先序遍历,哈夫曼树创建,编码用到的栈,递归函数,文本文件的读写,二进制的文件读写,字符转换。
2 哈夫曼编码
读取文本文件,统计词频,创建链表,根据权值(字符数)对链表进行从小到大排序,将排完序的链表构建成哈夫曼树,创建递归函数,通过二叉树先序遍历和栈实现编码。
3 压缩文件:文本文件转换为二进制文件
将文本文件里面的字符用编码替换,形成缓存01字符串,通过二进制转换十进制,将8个(一个字节)01字符串替换成一个整数,通过二进制文件的存储每个整数,这样实现了8个01字符变成只占1个字节的十六进制的整数。
4 解压文件:二进制文件转换为文本文件
与上边压缩文件相反,先读取二进制文件,将读取的整数转换为01字符串,通过反编码,将01字符串变成对应的字符,再将字符写入文本文件。
5 验证文件解压正确:
创建两个读取文件流,一起开始读取被压缩文件和解压后的文件,如果发现读取的字符不相同则解压失败。
三 概要设计
1、用于实现编码的栈
#pragma once
const long LENGTH=30;
class StackCode
{
public:
StackCode(void);
~StackCode(void);
//初始化栈
voidInitStack();
//获取当前栈顶字符
chargettop();
//压入栈内
voidpush(char c);
//推出栈外
charpop();
//数组
charcode[LENGTH*10000];
private:
inttop;
};
2哈夫曼树的节点 结构体
typedef struct HuffmanNode
{
char ch; /*字符*/
int weight,mark; /*weight为权值,mark为标志域*/
HuffmanNode *parent,*lchild,*rchild,*next;
}NodeTree,*LinkTree;
3 哈夫曼树编码压缩类
class Huffmanlink
{
public:
Huffmanlink(void);
~Huffmanlink(void);
//统计字符的链表和hufuman 树
LinkTree m_theList;
//创建字符链表
LinkTree CretaLink(ifstream &instream);
//对链表进行排序
LinkTree PreSort();
//遍历链表 并且返回树的叶子数
long traverseList();
//根据链表创建哈弗曼树
LinkTree CreatHuffmanTree();
//通过传入 字符栈 对栈进行编码
char Fuccode(LinkTree tree,StackCode&Thecode);
//对字符进行huffman 编码
void Huffmancoding(int n);
//压缩文件
void compress(char In_name[10],charOut_name[10]);
//解析二进制文件
unsigned char * decompress(charIn_name[10],char Out_name[10]);
//通过传入 字符栈 对栈进行解码(单个字符)
char FDecode(LinkTree tree,StackCode&Thecode ,char &u);
//文本的解码
void HuffmanDecode(unsigned char *TheCharAry,char nameOut[10]);
public:
//二进制文件的大小
long m_BaryFileSize;
//编码时补充的0的个数
longm_zeroNum;
//字符种类个数
long m_kindOfChar;
//总的字符个数 文件大小
long m_sizeOfFile;
//编码code 的数组
char **CharCode;
//被编码的字符数组
char *TheChar;
};
4 程序应用类
#pragma once
#include "Huffmanlink.h"
#include "fstream"
using namespace std;
class TheMyApp
{
public:
TheMyApp(void);
~TheMyApp(void);
HuffmanlinktheTree;
voidRun();
voidMenu();
//统计文件字符数
intstatisticsChar(void);
//打开文件
intOpenFile(void);
//文件名
charname_infile[10];
charname_outfile[10];
//输入 和 输出流
ifstreamm_in;
ofstreamm_out;
//字符权值排序
intPreMySort(void);
//字符编码
intHufucode(void);
//字符种类个数
intm_TheCharNum;
//压缩文件
intcompressFile(void);
//解压文件
intDecompressFile(void);
//验证解压文件成功
intcomparison(void);
//比较
boolFilecompar(ifstream & in_1,ifstream &in_2);
};
源码下载