题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1009

首先想到 确保模式串不出现 就是 确保每个位置的后缀不是该模式串。

为了dp,需要记录第 i 个位置的后缀已经有几位和模式串的前几位吻合了。

所以想到可以转移到 j+1 或 0 。

但其实不一定是0,因为可能和前面的接上。这里就要用kmp了!

注意可以和很多位置接上的时候,应该和最长的那个接上,而不是和每个 nxt 都接上,也不是什么能选择的。

知道了当前 j 能转移到哪些 j ,就可以矩阵优化了。

#include<iostream>
#include<cstdio>
#include<cstring>
using namespace std;
const int N=;
int n,m,mod,nxt[N],prn,ch[N];
struct Matrix{
int a[N][N];
Matrix(){memset(a,,sizeof a);}
Matrix operator * (const Matrix &b)const
{
Matrix c;
for(int i=;i<m;i++)//<m is enough
for(int k=;k<m;k++)
for(int j=;j<m;j++)
(c.a[i][j]+=a[i][k]*b.a[k][j]%mod)%=mod;
return c;
}
}r,ans;
void getnxt()
{
for(int i=;i<=m;i++)//i=2,or nxt[1]=1
{
int k;
for(k=nxt[i-];ch[k+]!=ch[i]&&k;k=nxt[k]);
nxt[i]=k+(ch[k+]==ch[i]);
}
for(int i=;i<m;i++)//i=0 //<m is enough
{
for(int j=;j<=;j++)
{
int k;
for(k=i;k&&ch[k+]!=j;k=nxt[k]);//k=i!!
if(ch[k+]==j)r.a[i][k+]++;//only keep 1,keep the longest
else r.a[i][]++;
// if(ch[k+1]==j)r.a[i][k+1]++;
// if(ch[1]==j)r.a[i][1]++;// when k=0
// else r.a[i][0]++;//
}
// if(i&&i!=m)r.a[i][i+1]++;//don't forget, and i!=0
}
}
int main()
{
scanf("%d%d%d",&n,&m,&mod);
for(int i=;i<=m;i++)scanf("%1d",&ch[i]);
getnxt();
// for(int i=0;i<m;i++)ans.a[i][i]=1;//!!
ans.a[][]=;
while(n){if(n&)ans=ans*r;r=r*r;n>>=;}
for(int i=;i<m;i++)(prn+=ans.a[][i])%=mod;
printf("%d\n",prn);
return ;
}

bzoj 1009 [HNOI2008]GT考试——kmp+矩阵优化dp的更多相关文章

  1. BZOJ 1009 [HNOI2008]GT考试 (KMP + 矩阵快速幂)

    1009: [HNOI2008]GT考试 Time Limit: 1 Sec  Memory Limit: 162 MBSubmit: 4266  Solved: 2616[Submit][Statu ...

  2. bzoj 1009: [HNOI2008]GT考试 -- KMP+矩阵

    1009: [HNOI2008]GT考试 Time Limit: 1 Sec  Memory Limit: 162 MB Description 阿申准备报名参加GT考试,准考证号为N位数X1X2.. ...

  3. BZOJ 1009 [HNOI2008]GT考试 (KMP+矩阵乘法)

    ---恢复内容开始--- 题目大意:给定一个由数字构成的字符串A(len<=20),让你选择一个长度为n(n是给定的)字符串X,一个合法的字符串X被定义为,字符串X中不存在任何一段子串与A完全相 ...

  4. 题解:BZOJ 1009 HNOI2008 GT考试 KMP + 矩阵

    原题描述: 阿申准备报名参加GT考试,准考证号为N位数 X1X2....Xn(0<=Xi<=9),他不希望准考证号上出现不吉利的数字.他的不吉利数学A1A2...Am(0<=Ai&a ...

  5. 洛谷P3193 GT考试 kmp+矩阵优化dp

    题意 求\(N\)位数字序列(可以有前导0)中不出现某\(M\)位子串的个数,模\(K\). \(N<=10^9,M<=20,K<=1000\) 分析 设\(dp[i][j]\)表示 ...

  6. BZOJ 1009 HNOI2008 GT考试 KMP算法+矩阵乘法

    标题效果:给定的长度m数字字符串s.求不包括子s长度n数字串的数目 n<=10^9 看这个O(n)它与 我们不认为这 令f[i][j]长度i号码的最后的字符串j位和s前者j数字匹配方案 例如,当 ...

  7. BZOJ.1009.[HNOI2008]GT考试(KMP DP 矩阵快速幂)

    题目链接 设f[i][j]为当前是第i位考号.现在匹配到第j位(已有j-1位和A[]匹配)的方案数 因为假如当前匹配j位,如果选择的下一位与A[j+1]不同,那么新的匹配位数是fail[j]而不是0, ...

  8. bzoj1009 GT考试 (kmp+矩阵优化dp)

    设f[i][j]是到第i位 已经匹配上了j位的状态数 然后通过枚举下一位放0~9,可以用kmp处理出一个转移的矩阵 然后就可以矩阵快速幂了 #include<bits/stdc++.h> ...

  9. BZOJ 1009: [HNOI2008]GT考试( dp + 矩阵快速幂 + kmp )

    写了一个早上...就因为把长度为m的也算进去了... dp(i, j)表示准考证号前i个字符匹配了不吉利数字前j个的方案数. kmp预处理, 然后对于j进行枚举, 对数字0~9也枚举算出f(i, j) ...

随机推荐

  1. 各种排序算法-用Python实现

    冒泡排序 # 冒泡排序 def bubble_sort(l): length = len(l) # 外层循环 length遍,内层循环少一遍 while length: for j in range( ...

  2. HDFS数据完整性

    数据完整性 Hadoop用户肯定都希望系统在存储和处理数据时不会丢失或损坏任何数据.尽管磁盘或网络上的每个I/O操作不太可能将错误引入自己正在读/写的数据中,但是如果系统中需要处理的数据量大到Hado ...

  3. javascript语言历史

    起初,web站点事实上只不过是一个静态的HTML文档集,这些文档之间仅依靠一些简单的超链接(Hyperlinks)绑定在一起. 但很快,随着Web业务的快速普及和增长,网站管理者越来越希望自己所创建的 ...

  4. 碰到错误Could not load the Tomcat server configuration at \Servers\MyEclipse Tomcat v8.5-config. The Servers project is closed.

    本人用的myeclipse是2017版. 可能解决的方法是: 双击MyEclipse Tomcat v8.5,然后就会弹出以下窗口,

  5. Js的cookie

    我们现在清除cookie缓存. 然后发起的请求观察: ============== ============= 已经有cookie的情况下发起请求: 我们在看看第一次没有缓存的情况下,返回的数据:

  6. java:输出流程printStream

    // TODO 自动生成的方法存根 //路径文件 File file = new File("F:"+File.separator+"work"+File.se ...

  7. PowerDesigner 学习

    1. 创建主键,不能为空,递增列,唯一约束(key 通过唯一索引) 数据库-->根据数据库的改动更新model  或者 根据修改后的model (比如新添加的字段)产生新sql代码 2.powe ...

  8. 5.3 Razor语法基础

    以往开发ASP.NET Web Form时,在ASPX页面上都会出现许多夹杂C#/VB.NET与HTML的情况,而先前使用<%...%>这种传统圆角括号的表示法会让HTML标签与ASP.N ...

  9. 机器学习(二)—支持向量机SVM

    1.SVM的原理是什么? SVM是一种二类分类模型.它的基本模型是在特征空间中寻找间隔最大化的分离超平面的线性分类器.(间隔最大是它有别于感知机) 试图寻找一个超平面来对样本分割,把样本中的正例和反例 ...

  10. AI探索(四)NumPy库的使用

    NumPy(Numerical Python) 是 Python 语言的一个扩展程序库,支持大量的维度数组与矩阵运算,此外也针对数组运算提供大量的数学函数库. umPy 是一个运行速度非常快的数学库, ...