洛谷P3193 GT考试 kmp+矩阵优化dp
题意
- 求\(N\)位数字序列(可以有前导0)中不出现某\(M\)位子串的个数,模\(K\)。
- \(N<=10^9,M<=20,K<=1000\)
分析
设\(dp[i][j]\)表示匹配串下标\(i\)匹配到模式串下标\(j\)时,满足要求的方案数;枚举匹配串的下一位是0~9中哪个数,若原先匹配串最远能匹配到模式串的下标为\(k\),加入这个数后最远能匹配到模式串的下标为\(j\),设\(a[k][j]\)为将匹配模式串下标从\(k\)变为\(j\)的数字个数,可以用\(next\)数组求出,dp转移方程就变成了
\]
这个式子可以用矩阵优化。
Code
#include<bits/stdc++.h>
#define fi first
#define se second
#define pb push_back
#define ll long long
using namespace std;
const int inf=1e9;
const int mod=1e9+7;
const int maxn=1e5+10;
int n,m,p,nex[21];
char s[21];
ll a[20][20],ret[20][20];
int find(int j,char k){
while(j&&s[j+1]!=k) j=nex[j];
if(k==s[j+1]) ++j;
return j;
}
void mul(ll a[20][20],ll b[20][20]){
ll tmp[20][20]={0};
for(int i=0;i<m;i++)
for(int j=0;j<m;j++)
for(int k=0;k<m;k++)
tmp[i][j]=(tmp[i][j]+a[i][k]*b[k][j]%p)%p;
for(int i=0;i<m;i++) for(int j=0;j<m;j++) a[i][j]=tmp[i][j];
}
void ksm(ll b){
for(int i=0;i<m;i++) ret[i][i]=1;
while(b){
if(b&1) mul(ret,a);
mul(a,a);
b>>=1;
}
}
int main(){
//ios::sync_with_stdio(false);
//freopen("in","r",stdin);
scanf("%d%d%d",&n,&m,&p);
scanf("%s",s+1);
for(int i=2,j=0;i<=m;i++){
while(j&&s[i]!=s[j+1]) j=nex[j];
if(s[i]==s[j+1]) ++j;
nex[i]=j;
}
for(int j=0;j<m;j++){
for(char k='0';k<='9';k++){
a[j][find(j,k)]++;
}
}ksm(n);
ll ans=0;
for(int i=0;i<m;i++){
ans=(ans+ret[0][i])%p;
}
printf("%lld\n",ans);
return 0;
}
洛谷P3193 GT考试 kmp+矩阵优化dp的更多相关文章
- bzoj 1009 [HNOI2008]GT考试——kmp+矩阵优化dp
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1009 首先想到 确保模式串不出现 就是 确保每个位置的后缀不是该模式串. 为了dp,需要记录 ...
- bzoj1009 GT考试 (kmp+矩阵优化dp)
设f[i][j]是到第i位 已经匹配上了j位的状态数 然后通过枚举下一位放0~9,可以用kmp处理出一个转移的矩阵 然后就可以矩阵快速幂了 #include<bits/stdc++.h> ...
- 洛谷P2365 任务安排(斜率优化dp)
传送门 思路: 最朴素的dp式子很好考虑:设\(dp(i,j)\)表示前\(i\)个任务,共\(j\)批的最小代价. 那么转移方程就有: \[ dp(i,j)=min\{dp(k,j-1)+(sumT ...
- 洛谷P2120 [ZJOI2007]仓库建设 斜率优化DP
做的第一道斜率优化\(DP\)QwQ 原题链接1/原题链接2 首先考虑\(O(n^2)\)的做法:设\(f[i]\)表示在\(i\)处建仓库的最小费用,则有转移方程: \(f[i]=min\{f[j] ...
- 【洛谷p3994】Highway 二分+斜率优化DP
题目大意:给你一颗$n$个点的有根树,相邻两个点之间有距离,我们可以从$x$乘车到$x$的祖先,费用为$dis\times P[x]+Q[x]$,问你除根以外每个点到根的最小花费. 数据范围:$n≤1 ...
- 洛谷4072 SDOI2016征途 (斜率优化+dp)
首先根据题目中给的要求,推一下方差的柿子. \[v\times m^2 = m\times \sum x^2 - 2 \times sum \times sum +sum*sum \] 所以\(ans ...
- 洛谷P3193 [HNOI2008]GT考试 kmp+dp
正解:kmp+dp+矩阵优化 解题报告: 传送门! 啊刚说想做矩阵优化dp的字符串题就找到辣QwQ虽然不是AC自动机的但都差不多嘛QwQ 首先显然可以想到一个dp式?就f[i][j]:凑出i位了,在s ...
- 洛谷模拟NOIP考试反思
洛谷模拟NOIP考试反思 想法 考了这么简单的试qwq然而依然emmmmmm成绩不好 虽然本次难度应该是大于正常PJ难度的但还是很不理想,离预估分数差很多qwq 于是就有了本反思嘤嘤嘤 比赛链接 原比 ...
- BZOJ 1009 [HNOI2008]GT考试 (KMP+矩阵乘法)
---恢复内容开始--- 题目大意:给定一个由数字构成的字符串A(len<=20),让你选择一个长度为n(n是给定的)字符串X,一个合法的字符串X被定义为,字符串X中不存在任何一段子串与A完全相 ...
随机推荐
- flask 接收参数小坑
前后端分离: 1.get方式: items = dict(request.args.items()) app_name = items["app_name"].strip() 或 ...
- T100——单据别的新增、修改设置
何为单据别,例如下图,新增的时候开窗选择单据别: 新增单据别: 1.首先在azzi600 系统分类码维护作业里面新增新的系统分类码(在系统分类码24下新增),如图: 2.在azzi910 作业基本数据 ...
- 《深入实践C++模板编程》之四——特例
1. 所谓模板特例,是针对符合某种条件的模板参数值集合另外声明的模板实现变体. template<typename T> class my_vector; template<> ...
- C#中word文档转html
var path = Request.Url.Host + ":" + Request.Url.Port + list[i].AnnexPath; //html保存路径 strin ...
- c#获取桌面路径和bin文件的路径
string path = Environment.GetFolderPath(Environment.SpecialFolder.DesktopDirectory): 生成的运行bin文件下的路径: ...
- 搭建自己的框架WedeNet(四)
WedeNet2018.Web-UI层:结构如下: 首先,在Controller中定义BaseController,以便加入统一处理逻辑,如下: using log4net; using System ...
- 深入理解hive之事务处理
事务的四个特性 1.automicity:原子性 2.consistency:一致性 3. isolation:独立性 4.durability:持久性 5.支持事务有几个条件需要满足:1.所有的事务 ...
- 深入理解hadoop之HDFS
深入理解hadoop之HDFS 刚刚才写完关于mapreduce的一篇博文,趁热打铁接下来聊聊HDFS.本博文参考资料为HADOOP权威指南第3版完版,博文如有错漏之处,敬请指正. HDFS即Hado ...
- vue axios异步请求django
1,配置请求路径 (1),vue中的请求路径要与django视图路径相同. (2),vue中的路由路径也要和django视图路径相同,比如视图路径为127.0.0.1:8000:home/index, ...
- Mongoose 使用Node操作MongoDB
Mongoose好处 可以为文档创建一个模式结构(Schema) 可以对模型中的对象/文档进行验证 数据可以通过类型转换转换为对象模型 可以使用中间件来应用业务逻辑挂钩 比Node原生的MongoDB ...