`
kenby
  • 浏览: 723807 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

poj 1521 huffman算法求最小编码

阅读更多

 

#include <stdio.h>
#include <string.h>

//#define DEBUG

#ifdef DEBUG
#define debug(...) printf( __VA_ARGS__) 
#else
#define debug(...)
#endif

#define MAX 256

typedef struct {
	int		weight;
	int		parent, lchild, rchild;
} huffman_node;

typedef struct {
	char	key;
	int 	weight;
	int		index;
} element;

huffman_node huffman_tree[MAX];

int		n;	/* 元素个数 */

/* 节点i的左子树和右子树已是最小堆, 此函数的作用是把以节点i为根的树调整为最小堆 */
void min_heapify(element *heap, int i) 
{
	int		child;	/* 较小的子节点 */
	element	elmt;
	
	elmt = heap[i];
	child = 2*i;
	while (child <= n) {
		if ((child+1) <= n && heap[child+1].weight < heap[child].weight) {
			child++;
		}
		if (heap[child].weight > elmt.weight)  break;
		heap[child/2] = heap[child];
		child *= 2;
	}
	heap[child/2] = elmt;
}

int extract_min(element *heap) 
{
	int index;

	index = heap[1].index;
	heap[1] = heap[n];
	n--;
	min_heapify(heap, 1);
	return index;
}

int insert(element *heap, int weight, int index)
{
	n++;
	heap[n].weight = weight;
	heap[n].index = index;
	min_heapify(heap, 1);
}

int main()
{
	char	str[MAX];
	char	*p;
	int		i, j, s1, s2, m;
	int 	length, code_length, str_length;
	element 	heap[MAX];
	float	rate;

	while (gets(str) && strcmp(str, "END") != 0) {
		memset(heap, 0, sizeof(heap));
		memset(huffman_tree, 0, sizeof(huffman_tree));
		/* 构造元素 */
		for (p = str; *p != '\0'; p++) {
			for (i = 1; heap[i].key != 0 && heap[i].key != *p; i++);
			heap[i].key = *p;
			heap[i].weight++;
			heap[i].index = i;
		}
		for (i = 1; heap[i].key != 0; i++) {
			huffman_tree[i].weight = heap[i].weight;
		}
		/* 计算元素个数 */
		for (i = 1; heap[i].key != 0; i++);
		n = i-1;
		m = 2*n;
		debug("%d个节点\n", n);
		
		//对元素建堆
		for (i = n/2; i > 0; i--) {
			min_heapify(heap, i);
			for (j = 1;  j <= n; j++) {
				debug("(%c:%d)  ", heap[j].key, heap[j].weight);
			}
			debug("\n");
		}

		//根据元素构造霍夫曼树
		for (i = n+1; i < m ; i++) {
			s1 = extract_min(heap); 
			s2 = extract_min(heap);
			debug("%d和%d号节点组成一组\n", s1, s2);
			huffman_tree[i].weight = huffman_tree[s1].weight + huffman_tree[s2].weight;
			huffman_tree[i].lchild = s1;
			huffman_tree[i].rchild = s2;
			huffman_tree[s1].parent = i;
			huffman_tree[s2].parent = i;
			insert(heap, huffman_tree[i].weight, i);
			for (j = 1;  j <= n; j++) {
				debug("(%c:%d)  ", heap[j].key, heap[j].weight);
			}
			debug("\n");
		}

		//根据每个叶子节点的高度, 求出编码长度
		code_length = 0;
		str_length = 8*strlen(str);
		for (i = 1; i <= m/2; i++) {
			j = i;
			length = 0;
			while (huffman_tree[j].parent) {
				j = huffman_tree[j].parent;
				length++;
			}
			if (length == 0) length = 1;
			code_length += length*huffman_tree[i].weight;	
		}
		rate = (float)str_length/(float)code_length;
		printf("%d %d %.1f\n", str_length, code_length, rate);
	}
	return 0;
}
分享到:
评论

相关推荐

    POJ 1751 求最小生成树prim算法(JAVA)

    标题 "POJ 1751 求最小生成树Prim算法(JAVA)" 提到的是一个编程挑战,涉及图论中的经典算法——Prim算法。在计算机科学中,Prim算法是用于寻找加权无向图的最小生成树的一种有效方法。最小生成树是一棵树形结构,...

    POJ算法题目分类

    POJ 算法题目分类 POJ 算法题目分类是指分类所有 POJ 题目的算法思想和解决方案,本文将对算法分类进行详细的介绍。 一、基本算法 基本算法是指最基础的算法思想,如枚举、贪心、递归和分治法、递推、构造法、...

    poj acm 题解 算法

    【标题】"poj acm 题解 算法"所指的是一份针对ACM(国际大学生程序设计竞赛)中POJ(Problemset Online Judge)平台上的题目进行解答的资源集合。ACM竞赛是全球范围内的一项编程竞赛,旨在提升大学生的算法设计和...

    POJ中级图算法所有题目【解题报告+AC代码】

    在编程竞赛领域,POJ(Programming Online Judge)是一个广受欢迎的在线编程平台,它提供了许多题目供参赛者解决,以提升编程和算法能力。本文主要关注的是“POJ中级图算法”的一系列题目及其解题报告和AC(Accepted...

    POJ各题算法分类和题目推荐 ACM必看

    POJ算法分类和题目推荐指南 本资源主要介绍了POJ(Online Judge)平台上各种算法分类和推荐题目,涵盖了动态规划、模拟、博弈等多种类型。以下是详细的知识点说明: 一、动态规划 动态规划是一种非常重要的算法...

    北大POJ初级-基本算法

    【北大POJ初级-基本算法】是一系列针对北京大学在线编程平台POJ的初级算法题目解题报告和通过(AC)代码的集合。这个资源对于学习算法基础和提升编程能力非常有帮助,尤其适合初学者。POJ是许多计算机科学与技术专业...

    最小费用流的原始对偶 (Primal-Dual) 算法.docx

    "最小费用流的原始对偶 (Primal-Dual) 算法" 该算法是融合了直接 ...13. POJ 3422:该题目是一个在线judge平台上的题目,要求使用 zkw 费用流算法来解决最小费用流问题,该题目是 zkw 费用流算法不擅长的一个例子。

    poj上算法题目分类

    根据提供的信息,我们可以将POJ(Peking Online Judge)平台上的算法题目按照不同的类别进行整理与解析。这对于希望系统性地提高自己算法能力的学习者来说非常有用。下面将基于给出的分类来详细介绍每一类算法的核心...

    POJ练习题算法分类

    根据提供的文件信息,我们可以将POJ练习题中的算法进行分类,并对每一类中的知识点进行详细的阐述。POJ(Pacific Ocean Judge)是一个在线编程平台,它提供了丰富的编程题目,旨在帮助学习者掌握各种基础算法和数据...

    北大POJ初级-图算法

    【北大POJ初级-图算法】是一系列针对北京大学在线编程平台POJ(Problem Online Judge)上的初级编程题目,重点在于图论算法的应用。这个解题报告集合了多种图算法的实现,帮助学习者掌握如何在实际问题中运用这些...

    Stoer-Wagner算法求全局最小割(模板)

    Stoer-Wagner 算法求全局最小割模板 Stoer-Wagner 算法是一种用于计算图的全局最小割的算法,该算法由 Daniel Stoer 和 Frank Wagner 于 1994 年提出。该算法可以应用于计算网络的最小割,例如计算社交网络中两个...

    POJ各题算法分类和题目推荐.pdf

    POJ各题算法分类和题目推荐.pdf

    poj算法题目实现.zip_algorithm_arrangement4hv_conditionyis_poj problems

    在本压缩包“poj算法题目实现.zip”中,包含了五个经典的编程竞赛题目,主要针对的是POJ(Programming Online Judge)平台。这些题目是程序员提升算法能力、锻炼编程技巧的重要资源。下面,我们将详细探讨每个题目...

    POJ 1077 算法

    标题中的“POJ 1078 算法”指的是北京大学在线判题系统(Problem Online Judge,简称POJ)中的第1077题,这通常是一个编程竞赛或者算法练习题目。POJ是一个供程序员练习算法、提交代码并获取运行结果的平台,主要...

    poj1087贪心算法实验报告

    在这个实验报告中,poj1087 题目就是一个典型的贪心算法应用实例。 题目描述了一个工厂需要将不同尺寸的产品(1*1 到 6*6)使用6*6的包裹进行包装,目标是最小化所需的包裹数量。贪心策略在此问题中的应用是逐个...

    POJ部分题解

    6. **图论算法**:包括最短路径算法(Dijkstra、Floyd-Warshall)、最小生成树算法(Prim、Kruskal)、拓扑排序等,这些都是解决图相关问题的常用工具。 7. **字符串处理**:KMP、Rabin-Karp、Boyer-Moore等字符串...

    北大POJ中级-基本算法

    【北大POJ中级-基本算法】解题报告与AC代码详解 北京大学的在线编程平台POJ(Problem Set of Peking University)是许多编程爱好者和学习者提升算法技能的重要平台。中级算法题目通常涵盖了一些基础但重要的算法...

    poj1251 最小生成树

    标题“poj1251 最小生成树”是一个编程竞赛题目,来源于著名的在线编程平台POJ(Programming Online Judge)。这个题目主要涉及图论中的一个经典算法问题——最小生成树(Minimum Spanning Tree, MST)。在图论中,...

    POJ 1789 最小生成树之prim算法

    标题中的“POJ 1789 最小生成树之prim算法”指的是一个在线编程竞赛题目,来源于普林斯顿开放在线课程(POJ)平台。该题目要求参赛者实现Prim算法,这是一种解决图论问题中寻找最小生成树的经典算法。最小生成树是在...

    ACM-POJ 算法训练指南

    2. **最小生成树**:Prim算法和Kruskal算法,用于构建图的最小生成树(poj1789, poj2485, poj1258, poj3026)。 3. **网络流**:Max-flow算法,用于解决最大流问题(poj1094)。 4. **拓扑排序**:解决有向无环图的...

Global site tag (gtag.js) - Google Analytics