Codeforces 1163D(kmp、dp)
要点
- \(dp[i][j][k]\)表示主串已经到第\(i\)位时,\(s\)匹配在\(j\)位、\(t\)匹配在\(k\)位的最大得分
- 本来就要试填一层循环,如果转移也写在循环里的化复杂度承受不了,于是开两个表kmp预处理一下。
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
char ch[1010], s[55], t[55];
int len, ls, lt, Ns[55], Nt[55];
int Ps[55][30], Pt[55][30];
int dp[1010][55][55], ans = 0xcfcfcfcf;
void GetNext(char *s, int len, int *Next, int P[][30]) {
Next[1] = 0;
for (int i = 2, j = 0; i <= len; i++) {
while (j && s[j + 1] != s[i]) j = Next[j];
if (s[i] == s[j + 1]) j++;
Next[i] = j;
}
for (int i = 0; i <= len; i++)
for (int c = 0; c < 26; c++) {
int j = i;
while (j && s[j + 1] != c + 'a') j = Next[j];
if (s[j + 1] == c + 'a') j++;
P[i][c] = j;
}
}
int main() {
scanf("%s%s%s", ch + 1, s + 1, t + 1);
len = strlen(ch + 1), ls = strlen(s + 1), lt = strlen(t + 1);
GetNext(s, ls, Ns, Ps), GetNext(t, lt, Nt, Pt);
memset(dp, 0xcf, sizeof dp);
dp[0][0][0] = 0;
for (int i = 0; i < len; i++)
for (int j = 0; j <= ls; j++)
for (int k = 0; k <= lt; k++)
for (int c = 0; c < 26; c++) {
if (ch[i + 1] != '*' && ch[i + 1] - 'a' != c) continue;
if (dp[i][j][k] == 0xcfcfcfcf) continue;
int a = Ps[j][c], b = Pt[k][c];
dp[i + 1][a][b] = max(dp[i + 1][a][b], dp[i][j][k] + (a == ls) - (b == lt));
}
for (int i = 0; i <= ls; i++)
for (int j = 0; j <= lt; j++)
ans = max(ans, dp[len][i][j]);
return !printf("%d\n", ans);
}
Codeforces 1163D(kmp、dp)的更多相关文章
- Codeforces 1168C(二进制、dp)
要点 '&'操作暗示二进制上按位思考 对于y为1的位,要求x和y之间要至少有两个此位为1的(包含x.y),这样&起来才不是0.而这些位中只要存在一个是ok的即可 dp去求每个x的每个位 ...
- codeforces 932E Team Work(组合数学、dp)
codeforces 932E Team Work 题意 给定 \(n(1e9)\).\(k(5000)\).求 \(\Sigma_{x=1}^{n}C_n^xx^k\). 题解 解法一 官方题解 的 ...
- 数的划分(DFS、DP)
https://www.luogu.com.cn/problem/P1025 题目描述 将整数n分成k份,且每份不能为空,任意两个方案不相同(不考虑顺序). 例如:n=7,k=3,下面三种分法被认为是 ...
- 九度OJ 1255:骰子点数概率 (递归、DP)
时间限制:1 秒 内存限制:32 兆 特殊判题:否 提交:316 解决:29 题目描述: 把n个骰子扔在地上,所有骰子朝上一面的点数之和为S.输入n,打印出S的所有可能的值出现的概率. 输入: 输入包 ...
- Codeforces 126B. Password(KMP,DP)
Codeforces 126B. Password 题意:一个字符串,找出最长的子串t,它既是前缀又是后缀,还出现在中间.输出t,不存在则输出Just a legend. 思路:利用KMP算法处理出n ...
- Codeforces Round #579 (Div. 3) Complete the Projects(贪心、DP)
http://codeforces.com/contest/1203/problem/F1 Examples input 1 - - output 1 YES input 2 - - output 2 ...
- Codeforces 808G Anthem of Berland(KMP+基础DP)
题意 给定一个字符串 \(s\) ,一个字符串 \(t\) ,其中 \(s\) 包含小写字母和 "?" ,\(t\) 只包含小写字母,现在把 \(s\) 中的问号替换成任意的小写字 ...
- codeforces 651C(map、去重)
题目链接:http://codeforces.com/contest/651/problem/C 思路:结果就是计算同一横坐标.纵坐标上有多少点,再减去可能重复的数量(用map,pair存一下就OK了 ...
- codeforces 721C (拓排 + DP)
题目链接:http://codeforces.com/contest/721/problem/C 题意:从1走到n,问在时间T内最多经过多少个点,按路径顺序输出. 思路:比赛的时候只想到拓排然后就不知 ...
随机推荐
- python读取文件后切片
from itertools import islice with open(“1.txt") as f: for a in islice(f,0,2): print(a)
- matlab添加当前文件夹到函数搜索目录
pwd表示当前路径p = genpath(folderName) 返回一个包含路径名称的字符向量,该路径名称中包含 folderName 以及 folderName 下的多级子文件夹. addpath ...
- 一些rtsp实现的开源代码
* live.com C/S C++ http://www.live555.com * darwin S C++ http://www.opensource.a ...
- hdu5776sum
题目连接 抽屉原理:如果现在有3个苹果,放进2个抽屉,那么至少有一个抽屉里面会有两个苹果 抽屉原理的运用 现在假设有一个正整数序列a1,a2,a3,a4.....an,试证明我们一定能够找到一段连续 ...
- kettle导数到user_用于left join_20160928
这篇博客主要是给mysql left join做铺垫,需要现在本地数据库创建一个users 数据表 然后去和 test_a03order表 left join 一.首先在local_db数据库先创建 ...
- boobmarklet
bookmarklet ,一般都称呼为小书签.它是一段 JavaScript 脚本,一般网络上的小书签都是一个链接,它的安装非常简单,只需要把链接拖到你的收藏夹里. 利用它,可以实现一些页面优化.性能 ...
- bzoj 4032 [ HEOI 2015 ] 最短不公共子串 —— 后缀自动机+序列自动机
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=4032 序列自动机其实就是每个位置记录一下某字母后面第一个出现位置,为了子序列能尽量长. 对字 ...
- mysql5.5换成mysql8.0
由于在建表钟发现有些语句就是录不进去,研究发现是因为5.5版本过低导致,就想换到5.7版本,结果一看8.0都出了,据官方说明8.0要比5系列快2倍网上,遂直接换成8.0了,不过这个过程真的心累. 1. ...
- windows文件同步工具
windows 文件同步工具: realTimesync freefilesync second copy second copy注册码: Name:爱学府软件园 注册码:15BF-E46C-67 ...
- [hdu2196]Computer树的直径
题意:求树中距离每个节点的最大距离. 解题关键:两次dfs,第一次从下向上dp求出每个节点子树中距离其的最大距离和不在经过最大距离上的子节点上的次大距离(后序遍历),第二次从上而下dp求出其从父节点过 ...