SDOI2021集训 R1 半夜 题解


\(O(n^3)\):对 \(XX\) 每个长度为 \(n\) 的字串与 \(Y\) 跑 LCS。设 \(f[i,j,k]\) 表示 \(X[i..j],Y[1..k]\) 的 LCS,暴力转移:\(f[i,j,k]=\max(f[i,j-1,k],f[i,j,k-1],[X[j]=Y[i]](f[i,j-1,k-1]+1))\)。
考虑两个性质:
\]
\]
证明没看懂,这里提供感性理解:
\(f[i-1,j,k]>f[i-1,j-1,k]\) 说明 \(X[j]\) 可以与 \(Y\) 中一个元素匹配,那么移动 \(i\) 对其他部分的影响相同,且不会影响它,那么 \(f[i,j,k]\) 仍 \(>f[i,j-1,k]\),第二个同理。
通过这两个性质可以发现一定存在分割点 \(p[j,k],q[j,k]\) 使 \(f[i,j,k]=f[i,j-1,k]+[i>p[j,k]]=f[i,j,k-1]+[i<q[j,k]]\),用 \(p[j,n]\) 就能 \(O(n^2)\) 递推出 \(f[i,i+n-1,n]\)。
注意这里 \(p,q\) 的两维与上两篇是反的,边界也不太相同。
考虑如何求 \(p,q\)。
设 \(F=f[i,j-1,k-1],P=p[j-1,k],Q=q[j,k-1]\)。分类讨论:
- \(X[j]\neq Y[k]\)
- \(P<Q\)
| \(i\) | \(P\) | \(Q\) | |
|---|---|---|---|
| \(f[i,j-1,k]\) | \(F+1\) | \(F+1\) | \(F\) |
| \(f[i,j,k-1]\) | \(F\) | \(F+1\) | \(F+1\) |
| \(f[i,j,k]\) | \(F+1\) | \(F+1\) | \(F+1\) |
其中 \(f[i,j,k]\) 的取值是根据最开始的暴力 DP 转移得到的,根据 \(f[i,j,k]\) 的取值就能得出 \(p[j,k]=Q,q[j,k]=P\)
其余三类也可以写出类似的表格,注意 \(X[j]=Y[k]\) 时 \(f[i,j,k]=f[i,j-1,k-1]+1\),这里就不一一列出了。
代码异常简洁:
const int N = 4e3+5;
int n;
char a[N],b[N];
int m,ans,p[N][N],q[N][N];
signed main() {
scanf("%d%s%s",&n,a+1,b+1); m = n+n; memcpy(a+n+1,a+1,n);
For(j,1,m) p[j][0] = j;
For(j,1,m) For(k,1,n) {
int P = p[j][k-1], Q = q[j-1][k];
if( a[j] != b[k] && P > Q ) p[j][k] = P, q[j][k] = Q;
else p[j][k] = Q, q[j][k] = P;
}
For(i,1,n) {
int now = 0;
For(j,i,i+n-1) now += i>p[j][n];
ckmax(ans,now);
}
write(ans);
return iocl();
}
SDOI2021集训 R1 半夜 题解的更多相关文章
- HihoCoder1338 A Game (区间DP)
<题目链接> 题目大意: 两个人轮流从一个序列中取数,他们都面临同样的二选一决策:是拿走最左边的数,还是拿走最右边的数?问先手最多能够得到的分数是多少. 解题分析: 一道比较经典的DP,因 ...
- 【题解】P4247 [清华集训]序列操作(线段树修改DP)
[题解]P4247 [清华集训]序列操作(线段树修改DP) 一道神仙数据结构(DP)题. 题目大意 给定你一个序列,会区间加和区间变相反数,要你支持查询一段区间内任意选择\(c\)个数乘起来的和.对1 ...
- 【某集训题解】【DAY 2 T3】与非
题目描述 作为一名新世纪共产主义的接班人,你认识到了资本主义的软弱性与妥协性,决定全面根除资本主义,跑步迈入共产主义.但是当你即将跨入共产主义大门的时候,遇到了万恶的资本家留下的与非电路封印,经过千辛 ...
- Nowcoder | [题解-N165]牛客网NOIP赛前集训营-普及组(第二场)
啊...表示一大早还没睡醒就开始打比赛(开始前一分钟的我还在桌子上趴着休眠)...表示题目思路清奇(尤其C题)...但是我还是太蒻了...\(D\)题暴力都没打...题解正式开始之前先\(\%\)一下 ...
- R1题解
估分 大佬们都去写题解了,我不写可能会被老师训诶.... 预计分数:100 + 100 + 5 + 100 + 25 + 100 = 430 实际 :80 + 100 + 0 + 100 + 25 + ...
- 暑假集训——cf热身赛部分题有感加其题解
刚刚开始集训,集训队队长暂时还没有拉专题,而是拉了部分codeforces上过题人数在2000左右的题组成了一场热身赛(其实就是一场练习),花了一天时间终于把它刷完了,其中很多题让我学到了很多骚操作, ...
- Yali7月集训Contest2 T1 Cube 题解
题目链接: 连我们都只有纸质题目...话说雅礼集训都是这样的吗... 大意 0维基本图形是一个点 1维基本图形是一条线段 2维基本图形是一个正方形 3维基本图形是一个正方体 4维基本图形是... 求\ ...
- SUST_ACM_2019届暑期ACM集训热身赛题解
问题A:Hello SUST! 知识点:基本输入输出 C/C++: #include <stdio.h> int main() { int n; scanf("%d", ...
- HZNU-ACM寒假集训Day12小结 数论入门 题解
算不出的等式 BJOI2012 看到这题 真没什么办法 无奈看题解 1.注意到p/q 联想到斜率 2.注意到 [ ] 联想到整点 注意到k在变化,构造一次函数 f(x)=p/q*x ,g(x)=q/p ...
随机推荐
- 预训练语言模型的前世今生 - 从Word Embedding到BERT
预训练语言模型的前世今生 - 从Word Embedding到BERT 本篇文章共 24619 个词,一个字一个字手码的不容易,转载请标明出处:预训练语言模型的前世今生 - 从Word Embeddi ...
- Commons-Beanutils利用链分析
前言 本篇开始介绍 commons-beanutils 利用链,注意Commons-Beanutils 不是Commons-Collections 不要看混了,首先来看一下,什么是 commons-b ...
- [WesternCTF2018]shrine(SSTI+过滤)
记一道存在过滤的模板注入的题.直接给源代码 import flask import os app = flask.Flask(__name__) app.config['FLAG'] = os.env ...
- 搭建NFS文件共享
1.概述: NFS(Network File System)意为网络文件系统,它最大的功能就是可以通过网络,让不同的机器不同的操作系统可以共享彼此的文件.简单的讲就是可以挂载远程主机的共享目录到本地, ...
- [C++]-string类的常用操作
代码 #include<iostream> #include<string> #include<algorithm> using namespace std; in ...
- Skywalking-06:OAL基础
OAL 基础知识 基本介绍 OAL(Observability Analysis Language) 是一门用来分析流式数据的语言. 因为 OAL 聚焦于度量 Service . Service In ...
- 用Autohotkey让Kitty命令行变得更好用
下面的脚本实现Win+K键激活一个输入框,给出了kitty命令行常用的几种格式,基本可分为两种:连接保存好的模板(session)和完全手工连接,前者用-load加Session名称,后者需要在命令行 ...
- Http协议中的CharacterEncoding、Content-Encoding和Transfer-Encoding
https://www.cnblogs.com/jinzhiming/p/5765672.html https://www.jianshu.com/p/e918a65b617f https://www ...
- SpringBoot开发九-生成验证码
需求介绍-生成验证码 先生成随机字符串然后利用Kaptcha API生成验证图片 代码实现 先在pom.xml引入 <dependency> <groupId>com.gith ...
- 北航OO第四单元——UML图解析
北航OO第四单元--UML图解析 作业要求简析 刚接触本次作业可能需要花上一会才能搞清楚到底是要我们写个啥,在这里简单说一下: UML图的保存格式.mdj文件是以json文件的形式存储的,将每一个Um ...