哈夫曼树实现哈夫曼编码(C++)

news2024/10/12 20:27:20

   题目要求:根据哈夫曼编码的原理,编写一个程序,在用户输入结点权值的基础上求赫夫曼编码,并能把给定的编码进行译码。

(1)初始化:从键盘输入一字符串(或读入一文件),统计出现的字符和每个字符出现的频率,将字符出现的频率作为结点的权值,建立哈夫曼树。对各个字符进行哈夫曼编码,最后打印输出字符及每个字符对应的哈夫曼编码。

(2)编码:利用已建好的哈夫曼树对“输入串”进行哈夫曼编码,最后打印输入串对应的哈夫曼编码(写入文件)。

(3)译码:利用已建好的哈夫曼树对给定的一串代码进行译码,并打印输出得到的字符串。(选作)

#include<iostream>
#include<map>
#include<set>
#include<algorithm>
using namespace std;
map<char, int> mp;
typedef struct node
{
	int data=0;
	char name;
}node;
node sum[100];
typedef struct Ht
{
	int w;
	char name;
	string code;
	int parent, lchild, rchild;
}Ht,*Htree;
int flag[100] = { 0 };
void Select(Htree& ht, int n, int& s1, int& s2)
{
	int min1 = 999, min2 = 999;
	for (int i = 1; i <= n; i++)//查找权值第一小的点
	{
		if (flag[i] == 0 && (ht[i].w < min1))
		{
			min1 = ht[i].w;
			s1 = i;
			ht[i].code = "0";//小的在左
		}
	}
	flag[s1] = 1;//标记该点移出
	for (int i = 1; i <= n; i++)//查找权值第二小的点
	{
		if (flag[i] == 0 && (ht[i].w < min2))
		{
			min2 = ht[i].w;
			s2 = i;
			ht[i].code = "1";//大的在右
		}
	}
	flag[s2] = 1;//标记该点移出
}
void Inithtree(Htree& ht, int n)//初始化
{
	if (n <= 1) return;
	int m = 2 * n - 1;
	ht = new Ht[m + 1];
	for (int i = 1; i <= m; i++)//将1到m点中的父亲、左孩子、右孩子下标都初始为0
	{
		ht[i].name = sum[i].name;
		ht[i].parent = 0, ht[i].lchild = 0, ht[i].rchild = 0;
		ht[i].w = sum[i].data;
	}
}
void Createtree(Htree& ht, int n)
{
	int s1, s2;
	for (int i = n + 1; i <= 2 * n - 1; i++)//循环n-1次,建树
	{
		Select(ht, i - 1, s1, s2);//查找两个父亲为0且权值最小的点,并返回序号s1、s2
		ht[s1].parent = i, ht[s2].parent = i;//s1、s2父亲改为i
		ht[i].lchild = s1, ht[i].rchild = s2;//s1、s2分别作为i的左右孩子
		ht[i].w = ht[s1].w + ht[s2].w;//i的权值为左右孩子权值之和
	}
}
void Printtree(Htree& ht, int n)//打印
{
	for (int i = 1; i <= 2 * n - 1; i++)
		cout << ht[i].name << " " << ht[i].w << " " << ht[i].parent << " " << ht[i].lchild << " " << ht[i].rchild << endl;
}
void bianma(Htree& ht, int n)//编码
{
	for (int i = 1; i <= n; i++)
	{
		int parent = ht[i].parent;//获取该点父亲
		while (parent != 0)//不到根节点
		{
			ht[i].code = ht[parent].code + ht[i].code;//编码等于父亲加上自身
			parent = ht[parent].parent;//找父亲的父亲
		}
	}
}
int main()
{
	Htree h;
	string str;
	cin >> str;
	for (int i = 0; i < str.length(); i++)
	{
		mp[str[i]]++;
	}
	int k = 1;
	int n = mp.size();//字符种类
	for (auto i : mp)
	{
		sum[k].name = i.first;
		sum[k++].data = i.second;
	}
	Inithtree(h, n);
	Createtree(h, n);
	//Printtree(h, n);
	bianma(h, n);
	cout << "编码:" << endl;
	for (int i = 1; i <= n; i++)//输出各字符的编码
		cout << h[i].name << ": " << h[i].code << endl;
	for (int i = 0; i < str.length(); i++)//字符串转为编码
	{
		for (int j = 1; j <= n; j++)
		{
			if (str[i] == h[j].name)
			{
				cout << h[j].code << " ";
				break;
			}
		}
	}
	cout << endl;
	string str1;
	string str2[100];
	int d = 0;
	cout << "译码:" << endl;
	cin >> str1;
	for (int i = 0; i < str1.length(); i++)
	{
		str2[d] += str1[i];
		for (int j = 1; j <= n; j++)
		{
			if (str2[d] == h[j].code)
			{
				cout << h[j].name;
				d++;
				break;
			}
		}
	}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1108706.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【微服务】spring webflux使用详解

目录 一、webflux介绍 1.1 什么是webflux 1.2 什么是响应式编程 1.3 webflux特点 二、Java9中响应式编程 2.1 定义事件流源 2.2 实现订阅者 三、Spring Webflux介绍 四、Reactor 介绍 五、Reactor 常用API操作 5.1 Flux 创建流操作API 5.2 Flux响应流的订阅 5.3 Fl…

PHP WAP餐厅点餐系统mysql数据库web结构apache计算机软件工程网页wamp

一、源码特点 PHP餐厅点餐系统是一套完善的web设计系统&#xff0c;对理解php编程开发语言有帮助&#xff0c;系统具有完整的源代码和数据库&#xff0c;系统主要采用B/S模式开发。 PHP WAP餐厅点餐系统 代码 https://download.csdn.net/download/qq_41221322/88440001 二、…

Kubeadm部署k8s集群 kuboard

目录 主机准备 主机配置 修改主机名&#xff08;三个节点分别执行&#xff09; 配置hosts&#xff08;所有节点&#xff09; 关闭防火墙、selinux、swap、dnsmasq(所有节点) 安装依赖包&#xff08;所有节点&#xff09; 系统参数设置(所有节点) 时间同步(所有节点) 配…

【密码学】第三章、分组密码

DES、IDEA、AES、SM4 1、分组密码定义&#xff08;按照五个组成部分答&#xff09; 密钥空间&#xff1a;属于对称加密算法kekd明密文空间&#xff1a;将明文划分为m比特的组&#xff0c;每一块依次进行加密加解密算法&#xff1a;由key决定一个明文到密文的可逆映射 2、发展…

C语言入门-1.1 C语言概述

想要学好一门计算机编程语言&#xff0c;就和谈一个女朋友是一样的&#xff0c;需要对其深入了解。 1、计算机语言 &#xff08;1&#xff09;什么是计算机语言&#xff1f; 顾名思义&#xff0c;就是计算机之间交流的语言&#xff0c;就和人一样&#xff0c;咱们都是使用普通…

中文编程开发语言工具编程实际案例:美发店会员管理系统软件编程实例

中文编程开发语言工具编程实际案例&#xff1a;美发店会员管理系统软件编程实例 中文编程开发语言工具编程实际案例&#xff1a;美发店会员管理系统软件编程实例。 软件功能&#xff1a; 1、系统设置&#xff1a;参数设定&#xff0c;账号及权限设置&#xff0c;系统初始化&a…

PHP的四层架构

PHP的4层架构是一种软件设计模式&#xff0c;用于将一个PHP应用程序划分为不同的层次&#xff0c;以实现解耦、可扩展和易于维护的代码结构。这个架构通常由以下四个层次组成&#xff1a; 1、 表现层&#xff08;Presentation Layer&#xff09;&#xff1a; 表现层是与用户直…

动态规划解股票类型

文章目录 单只股票买卖多次买卖单只股票最多两次买卖股票最多买k次含冷静期含手续费 单只股票买卖 买卖股票的最佳时机 关键思路&#xff1a;找到一个值&#xff0c;他与之后的最大值之差最大。 用minprice记录最小的值&#xff0c;用maxprofit记录最大的收益。 想清楚一个点…

麒麟kylinOS 2303制作自定义免交互安装镜像

原文链接&#xff1a;麒麟kylinOS 2303制作自定义免交互安装镜像 hello&#xff0c;大家好啊&#xff0c;今天给大家带来一篇麒麟kylinOS 2303制作自定义免交互ISO安装镜像的文章&#xff0c;内容相对来说比较简单&#xff0c;测试安装了一个360浏览器软件&#xff0c;后续复杂…

c语言练习93:环形链表的约瑟夫问题

环形链表的约瑟夫问题 环形链表的约瑟夫问题_牛客题霸_牛客网 描述 编号为 1 到 n 的 n 个人围成一圈。从编号为 1 的人开始报数&#xff0c;报到 m 的人离开。 下一个人继续从 1 开始报数。 n-1 轮结束以后&#xff0c;只剩下一个人&#xff0c;问最后留下的这个人编号是…

【CesiumforUnreal插件】UE5 快速构建Cesium场景 快速入门!!!

目录 0 引言1 快速入门1.1 准备1.2 安装Cesium for Unreal插件并创建一个项目1.3 准备关卡并添加地形和纹理1.4 添加3D建筑到场景中1.5 探索场景 &#x1f64b;‍♂️ 作者&#xff1a;海码007&#x1f4dc; 专栏&#xff1a;CesiumforUnreal专栏&#x1f4a5; 标题&#xff1a…

论坛介绍|COSCon'23开源商业(V)

众多开源爱好者翘首期盼的开源盛会&#xff1a;第八届中国开源年会&#xff08;COSCon23&#xff09;将于 10月28-29日在四川成都市高新区菁蓉汇举办。本次大会的主题是&#xff1a;“开源&#xff1a;川流不息、山海相映”&#xff01;各位新老朋友们&#xff0c;欢迎到成都&a…

C++数据结构X篇_17_C++实现二叉树的非递归遍历(企业链表实现栈,利用栈的先进后出特点实现二叉树的非递归遍历)

本篇参考C实现二叉树的非递归遍历进行整合介绍。 在C数据结构X篇_14_二叉树的递归遍历&#xff08;先序遍历、中序遍历、后续遍历方法介绍&#xff1b;举例&#xff1b;代码实现&#xff09;中我们实现二叉树通过递归遍历实现了先序、中序与后续遍历&#xff0c;那么如何通过非…

Confluence 自定义博文列表

1. 概述 Confluence 自有博文列表无法实现列表自定义功能&#xff0c;实现该需求可采用页面中引用博文宏标签控制的方式 2. 实现方式 功能入口&#xff1a; Confluence →指定空间→创建页面 功能说明&#xff1a; &#xff08;1&#xff09;页面引用博文宏 &#xff08;…

标准化助推开源发展丨九州未来参编开源领域4项团体标准正式发布

在数字中国及数字经济时代的大背景下&#xff0c;开源逐步成为各行业数字化发展的关键模式。在开源产业迅速发展的同时&#xff0c;如何评估、规范开源治理成为行业极度关注的问题。 近日&#xff0c;中电标2023年第27号团体标准公告正式发布&#xff0c;九州未来作为起草单位…

云表:只需3步,让你搞懂低代码和传统开发有什么区别

自2014年Forrester明确提出低代码&#xff08;Low-Code&#xff09;概念以来&#xff0c;这个领域已经引起了广泛的关注&#xff0c;并逐渐受到越来越多的重视。近年来&#xff0c;低代码因为其低开发门槛、易用性等优点&#xff0c;赢得了众多投资研究机构和企业用户的青睐&am…

【Vue】终结v-model

v-model修饰符 .lazy 默认 v-model 是输入框内容每次改变都会更新数据 加了 .lazy 后,只有在输入框失去焦点时才会更新数据 例如输入用户名,只有离开输入框时才保存用户名 // 输入的时候不会立即加载&#xff0c;等失去焦点时会加载 <input v-model.lazy"msg"…

Python打造一个词云制作软件

文章目录 参数字典布局测试结果 参数字典 自从做了热榜的词云之后&#xff0c;就越来越觉得词云的表达力真的很强&#xff0c;所以合计是不是可以为WordCloud做一个界面&#xff0c;来更加直观地操作。 既然以WordCloud为核心&#xff0c;那么界面的组件自然要和WordCloud的参…

GEO生信数据挖掘(九)肺结核数据-差异分析-WGCNA分析(900行代码整理注释更新版本)

第六节&#xff0c;我们使用结核病基因数据&#xff0c;做了一个数据预处理的实操案例。例子中结核类型&#xff0c;包括结核&#xff0c;潜隐进展&#xff0c;对照和潜隐&#xff0c;四个类别。第七节延续上个数据&#xff0c;进行了差异分析。 第八节对差异基因进行富集分析。…

王道计算机考研 操作系统学习笔记篇章一:操作系统概念

目录 操作系统的概念 操作系统的功能和目标 操作系统的特征 并发 共享 虚拟 异步 操作系统的发展和分类 三大阶段 手工操作阶段 批次处理阶段—单道批处理系统 批处理阶段—多道批处理系统 操作系统分类 分时操作系统 实时操作系统 其他操作系统 操作系统的运行机制 预备知识 …