第九次CSP第四题 - 压缩编码
给定一段文字,已知单词a1, a2, …, an出现的频率分别t1, t2, …, tn。可以用01串给这些单词编码,即将每个单词与一个01串对应,使得任何一个单词的编码(对应的01串)不是另一个单词编码的前缀,这种编码称为前缀码。
使用前缀码编码一段文字是指将这段文字中的每个单词依次对应到其编码。一段文字经过前缀编码后的长度为:
L = a1的编码长度 × t1 + a2的编码长度 × t2 + … + an的编码长度 × tn。
定义一个前缀编码为字典序编码,指对于1 ≤ i < n,ai的编码(对应的01串)的字典序在ai+1编码之前,即a1,a2, …, an的编码是按字典序升序排列的。
例如,文字E A E C D E B C C E C B D B E中, 5个单词A、B、C、D、E出现的频率分别为1, 3, 4, 2, 5,则一种可行的编码方案是A:000, B:001, C:01, D:10, E:11,对应的编码后的01串为1100011011011001010111010011000111,对应的长度L为3×1+3×3+2×4+2×2+2×5=34。
在这个例子中,如果使用哈夫曼(Huffman)编码,对应的编码方案是A:000, B:01, C:10, D:001, E:11,虽然最终文字编码后的总长度只有33,但是这个编码不满足字典序编码的性质,比如C的编码的字典序不在D的编码之前。
在这个例子中,有些人可能会想的另一个字典序编码是A:000, B:001, C:010, D:011, E:1,编码后的文字长度为35。
请找出一个字典序编码,使得文字经过编码后的长度L最小。在输出时,你只需要输出最小的长度L,而不需要输出具体的方案。在上面的例子中,最小的长度L为34。
显然,不能对已给出的频率进行排序了,因为一旦这样,就不能满足编码字典序的要求。
正如网上的很多题解所说,这是一道DP问题。
dp[i][j]表示:对[i,j]这一段上的字符进行合并,从而合并成一棵二叉树,进而得到编码,这段文字编码后的长度(并且这种合并方案是[i,j]上进行的所有合并方案中,对应的长度最小的)。
sum[i][j]表示:freq[i] + freq[i+1] + …… + freq[j];
#include<cstdio>
#include<cstring>
#include<algorithm>
#define MAXN 1005
#define INF 0x7fffffff
using namespace std;
typedef long long ll;
ll dp[MAXN][MAXN],sum[MAXN];
//状态转移方程:dp[i][j]=min(dp[i][k],dp[k+1][j]) + sum[i][j] ; (k= i to j-1)
int n;
int main()
{
scanf("%d",&n);
sum[]=;
for(int i=;i<=n;i++)
{
ll tmp;
scanf("%lld",&tmp);
sum[i]=sum[i-]+tmp;
}
/*
使用三重循环
最外重为每次归并的堆数的循环,从2到n;
第二重为dp[i][j]中的i的循环;
最内重为 k= i to j-1 的循环;
*/
for(int i=;i<=n;i++) dp[i][i]=; //初始化dp[i][i]
for(int v=;v<=n;v++)
{
for(int i=;i<=n-(v-);i++)
{
int j=i+(v-);
dp[i][j]=INF;
for(int k=i;k<=j-;k++)
{
dp[i][j]=min(dp[i][j],dp[i][k]+dp[k+][j]);
}
dp[i][j]+=sum[j]-sum[i-];
}
}
if(n==) printf("%d\n",sum[]);
else printf("%lld\n",dp[][n]);
}
第九次CSP第四题 - 压缩编码的更多相关文章
- 网络流二十四题,题解summary
没有全部写完,有几题以后再补吧. 第一题:最简单的:飞行员配对方案问题 讲讲这个题目为什么可以用网络流? 因为这个题目是要进行两两之间的匹配,这个就可以想到用二分图匹配,二分图匹配又可以用网络流写. ...
- Java-集合(没做出来)第四题 (List)写一个函数reverseList,该函数能够接受一个List,然后把该List 倒序排列。 例如: List list = new ArrayList(); list.add(“Hello”); list.add(“World”); list.add(“Learn”); //此时list 为Hello World Learn reverseL
没做出来 第四题 (List)写一个函数reverseList,该函数能够接受一个List,然后把该List 倒序排列. 例如: List list = new ArrayList(); list.a ...
- 经典算法题每日演练——第十四题 Prim算法
原文:经典算法题每日演练--第十四题 Prim算法 图论在数据结构中是非常有趣而复杂的,作为web码农的我,在实际开发中一直没有找到它的使用场景,不像树那样的频繁使用,不过还是准备 仔细的把图论全部过 ...
- NOIP2010-普及组复赛-第四题-三国游戏
题目描述 Description 小涵很喜欢电脑游戏,这些天他正在玩一个叫做<三国>的游戏. 在游戏中,小涵和计算机各执一方,组建各自的军队进行对战.游戏中共有 N 位武将(N为偶数且不 ...
- CTF---Web入门第十四题 忘记密码了
忘记密码了分值:20 来源: Justatest 难度:中 参与人数:7706人 Get Flag:2232人 答题人数:2386人 解题通过率:94% 找回密码 格式:SimCTF{ } 解题链接: ...
- hiho_offer收割18_题解报告_差第四题
I.求逆元欧几里得方法 II.模拟细心+耐心 *本人感悟:自己的错误在于:对于这道模拟题没有耐心静下来一字一字看题,一行一行调错,一步一步调试,我要引以为戒. III.dpf[i][j][k]=max ...
- 第六届蓝桥杯java b组第四题
第四题 两个整数做除法,有时会产生循环小数,其循环部分称为:循环节. 比如,11/13=6=>0.846153846153….. 其循环节为[846153] 共有6位. 下面的方法,可以求出循环 ...
- 关于2018年第九届蓝桥杯[C++省赛B组][第四题:测试次数]的疑问
题目来源:https://blog.csdn.net/qq_34202873/article/details/79784548 #标题:测试次数#x星球的居民脾气不太好,但好在他们生气的时候唯一的异常 ...
- 【leetcode 简单】 第九十四题 左叶子之和
计算给定二叉树的所有左叶子之和. 示例: 3 / \ 9 20 / \ 15 7 在这个二叉树中,有两个左叶子,分别是 9 和 15,所以返回 24 # Definition for a binary ...
随机推荐
- Spring集成Mybatis,spring4.x整合Mybatis3.x
Spring集成Mybatis,spring4.x整合Mybatis3.x ============================== 蕃薯耀 2018年3月14日 http://www.cnblo ...
- PHP代码审计笔记--弱类型存在的安全问题
0x01 前言 PHP 是一门弱类型语言,不必向 PHP 声明该变量的数据类型,PHP 会根据变量的值,自动把变量转换为正确的数据类型. 弱类型比较,是一个比较蛋疼的问题,如左侧为字符串,右侧为一个整 ...
- wordpress for sae
帮人建个站,准备用sae+wordpess,小研究一下 http://sae.sina.com.cn/?m=apps&a=detail&aid=1 http://wp4sae.org/ ...
- java web当中表单提交到后台出现乱码的解决方法
1.如果提交方式为post,想不乱码,只需要在服务器端设置request对象的编码即可,客户端以哪种编码提交的,服务器端的request对象就以对应的编码接收,比如客户端是以UTF-8编码提交的,那么 ...
- tomcat端口被占用的两个解决方法
tomcat 的 8080 端口经常会被占用,解决办法两个: 1.关闭占用8080端口的进程:8080端口被占用的话执行startup.bat会报错,可在cmd下执行netstat -ano命令查看8 ...
- Oracle和Mysql中mybatis模糊匹配查询区别
1.Oracle AND NAME LIKE '%'||#{name}||'%' 2.Mysql AND NAME LIKE "%"#{name}"%"
- JSP基本用法(二)隐含对象
一.摘要 在JSP容器中生成的Servlet类的_jspService()方法中,定义了几个对象,在编写JSP页面时我们可以使用这些隐含对象. PageContext pageContext = nu ...
- 【cs229-Lecture9】经验风险最小化
写在前面:机器学习的目标是从训练集中得到一个模型,使之能对测试集进行分类,这里,训练集和测试集都是分布D的样本.而我们会设定一个训练误差来表示测试集的拟合程度(训练误差),虽然训练误差具有一定的参考价 ...
- R语言(入门小练习篇)
问题: 一组学生参加了数学.科学和英语考试.为了给所有的学生确定一个单一的成绩衡量指标,需要将这些科目的成绩组合起来.另外,还想将前20%的学生评定为A,接下来20%的学生评定为B,以此类推.最后,希 ...
- Android自定义组件——四个方向滑动的菜单实现
今天无意中实现了一个四个方向滑动的菜单,感觉挺好玩,滑动起来很顺手,既然已经做出来了就贴出来让大家也玩弄一下. 一.效果演示 (说明:目前没有安装Android模拟器,制作的动态图片太卡了,就贴一下静 ...