洛谷P4302 [SCOI]字符串折叠 [字符串,区间DP]
字符串折叠
题目描述
折叠的定义如下:
- 一个字符串可以看成它自身的折叠。记作S = S
- X(S)是X(X>1)个S连接在一起的串的折叠。记作X(S) = SSSS…S(X个S)。
如果A = A’, B = B’,则AB = A’B’ 例如,因为3(A) = AAA, 2(B) = BB,所以3(A)C2(B) = AAACBB,而2(3(A)C)2(B) = AAACAAACBB
给一个字符串,求它的最短折叠。例如AAAAAAAAAABABABCCD的最短折叠为:9(A)3(AB)CCD。
输入输出格式
输入格式:
仅一行,即字符串S,长度保证不超过100。
输出格式:
仅一行,即最短的折叠长度。
输入输出样例
说明
一个最短的折叠为:2(NEERC3(YES))
分析:
K_lord的考试里面出的题目。考的时候直接弃疗。。。(先膜一波老余AK%%%)
需要用区间DP来做,首先定义动规数组f[l][r],表示从l到r这一段区间内的字符串折叠后能得到的最短结果。那么枚举折叠的区间,然后枚举左右区间,再枚举可折叠的长度,也就是枚举区间长度的所有因数,然后进行判断该区间是否可以折叠,如果可以则进行状态转移。值得注意的是,转移完以后还需要在进行依次断点枚举,表示将该区间分成两次折叠,看能否得到最短折叠。当然,蒟蒻不擅长动规,还是听了老余讲课,又参考了大佬的博客才弄懂的。如果上面的思路不太懂,就直接看代码吧,代码好懂多了。
Code:
#include<bits/stdc++.h>
using namespace std;
char s[];int f[][];
inline bool check(int l,int r,int k)
{
for(int i=l+k,p=;i<=r;i++,p=(p+)%k)
if(s[i]!=s[l+p])return false;
return true;
}
inline int get(int x)
{int ret=;while(x)x/=,ret++;return ret;}
int main()
{
memset(f,0x7f,sizeof(f));
scanf("%s",s+);int n=strlen(s+);
for(int i=;i<=n;i++)f[i][i]=;
for(int i=;i<=n;i++)
for(int l=;l+i-<=n;l++){
int r=l+i-;
for(int k=;k*k<=i;k++){
if(i%k==){
if(check(l,r,i/k))f[l][r]=min(f[l][r],f[l][l+i/k-]+get(k));
if(check(l,r,k))f[l][r]=min(f[l][r],f[l][l+k-]+get(i/k));}}
for(int k=l;k<=r;k++)
f[l][r]=min(f[l][r],f[l][k]+f[k+][r]);}
printf("%d",f[][n]);return ;
}
洛谷P4302 [SCOI]字符串折叠 [字符串,区间DP]的更多相关文章
- luogu4302字符串折叠题解--区间DP
题目链接 https://www.luogu.org/problemnew/show/P4302 分析 很明显一道区间DP题,对于区间\([l,r]\)的字符串,如果它的字串是最优折叠的,那么它的最优 ...
- [SCOI2003]字符串折叠(区间dp)
P4302 [SCOI2003]字符串折叠 题目描述 折叠的定义如下: 一个字符串可以看成它自身的折叠.记作S = S X(S)是X(X>1)个S连接在一起的串的折叠.记作X(S) = SSSS ...
- bzoj 1090 [SCOI2003]字符串折叠(区间DP)
[题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=1090 [题意] 给定一个字符串,问将字符串折叠后的最小长度. [思路] 设f[i][j ...
- [bzoj1090][SCOI2003]字符串折叠_区间dp
字符串折叠 bzoj-1090 SCOI-2003 题目大意:我说不明白...链接 注释:自己看 想法:动态规划 状态:dp[i][j]表示从第i个字符到第j个字符折叠后的最短长度. 转移:dp[l] ...
- [luogu1090 SCOI2003] 字符串折叠(区间DP+hash)
传送门 Solution 区间DP,枚举断点,对于一个区间,枚举折叠长度,用hash暴力判断是否能折叠即可 Code #include <cstdio> #include <cstr ...
- 【洛谷】P1063 能量项链【区间DP】
P1063 能量项链 题目描述 在Mars星球上,每个Mars人都随身佩带着一串能量项链.在项链上有N颗能量珠.能量珠是一颗有头标记与尾标记的珠子,这些标记对应着某个正整数.并且,对于相邻的两颗珠子, ...
- 洛谷 P1220 关路灯 (贪心+区间dp)
这一道题我一直在想时间该怎么算. 看题解发现有个隐藏的贪心. 路径一定是左右扩展的,左右端点最多加+1(我竟然没发现!!) 这个性质非常重要!! 因此这道题用区间dp f[i][j]表示关完i到j的路 ...
- 1090. [SCOI2003]字符串折叠【区间DP】
Description 折叠的定义如下: 1. 一个字符串可以看成它自身的折叠.记作S S 2. X(S)是X(X>1)个S连接在一起的串的折叠.记作X(S) SSSS…S(X个S). ...
- bzoj 1090: [SCOI2003]字符串折叠【区间dp】
设f[i][j]为区间(i,j)的最短长度,然后转移的话一个是f[i][j]=min(j-i+1,f[i][k]+f[k+1][j]),还有就是把(k+1,j)合并到(i,k)上,需要判断一下字符串相 ...
随机推荐
- Android之极光推送发送自定义消息
Android端实现主要代码: <span style="font-size:14px;">import java.io.IOException; import jav ...
- ZooKeeper配额指南(十)
配额 ZK有命名空间和字节配额.你可以使用ZooKeeperMain类来设置配额.ZK打印警告信息如果用户超过分配给他们的配额.这些信息被打印到ZK的日志中. $java -cp zookeeper. ...
- ZooKeeper翻译(一)
欢迎来到Apache ZooKeeper的世界 Apache Zookeeper是一个为了开发和维护一个开源的服务的一个尝试,这个服务使高可用的分布式协作成为可能. ZooKeeper是什么? Zoo ...
- CodeForces527D. Fuzzy Search
time limit per test:3 seconds memory limit per test:256 megabytes input:standard input output:standa ...
- 【51NOD-0】1137 矩阵乘法
[算法]简单数学 [题解] 对于A*B=C C中第i行第j列的数字由A中第i行和B中的j列的数字各自相乘后相加得到. 所以两个矩阵能相乘要求A的列数等于B的行数,复杂度为O(n3). #include ...
- LCA入门题集小结
题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=2586 题目: How far away ? Time Limit: 2000/1000 MS (Jav ...
- 表格td内容超出宽度显示... table-layout: fixed;
td宽度用百分比固定好的时候,即使设置了 white-space:nowrap;/*文本不会换行,在同一行显示*/ overflow:hidden;超出隐藏 text-overflow:ellipsi ...
- js_返回上一页(兼容苹果手机)
返回上一页功能是常见的功能. 常用的有以下三种代码: window.history.go(-1); //返回上一页 window.history.back(); //返回上一页 //如果要强行刷新的话 ...
- 【Python学习笔记】异常处理try-except
Python异常处理 我们一般使用try-except语句来进行异常处理. 使用except Exception as err可以统一捕捉所有异常,而也可以分开处理单个异常. # 分开捕捉单个异常 t ...
- Reactor与Proactor区别
如网络编程中accept之后等待数据到达,并且读取数据为例: Reactor: 基于同步IO 1. 线程等待读取socket数据,将socketfd添加到事件分派器中,如添加到epoll: 2. 事件 ...