Description

Alice想要得到一个长度为 \(n\) 的序列,序列中的数都是不超过 \(m\) 的正整数,而且这 \(n\) 个数的和是 \(p\) 的倍数。

Alice还希望,这 \(n\) 个数中,至少有一个数是质数。

Alice想知道,有多少个序列满足她的要求。

Input

一行三个数,\(n,m,p\)。

Output

一行一个数,满足Alice的要求的序列数量,答案对 \(20170408\) 取模。

Sample Input

3 5 3

Sample Output

33

HINT

对 \(20\%\) 的数据,\(1\leq n,m\leq100\)

对 \(50\%\) 的数据,\(1\leq m \leq 100\)

对 \(80\%\) 的数据,\(1\leq m\leq 10^6\)

对 \(100\%\) 的数据,\(1\leq n \leq 10^9,1\leq m \leq 2\times 10^7,1\leq p\leq 100\)

Solution

设 \(f[i][j]\) 表示前 \(i\) 位之和模 \(p\) 等于 \(j\) 的方案数,\(g[i]\) 表示在模 \(p\) 意义下等于 \(i\) 的数的个数,有

\[f[i][j]=f[i-1][k]\cdot g[(j+p-k)\bmod p],0\le k < p
\]

可构造出转移矩阵

\[\begin{bmatrix}
g_0&g_{p-1}&\cdots&g_{1}\\
g_{1}&g_{0}&\cdots&g_{2}\\
\vdots&\vdots&\ddots&\vdots\\
g_{p-1}&g_{p-2}&\cdots&g_{0}
\end{bmatrix}
\begin{bmatrix}
f_0\\
f_1\\
\vdots\\
f_{p-1}
\end{bmatrix}
\]

最后用总的答案减去不包含质数的答案。

再科普一下NTT做法:

\[(g_0+g_1x+g_2x^2+\cdots+g_{p-1}x^{p-1})^{n-1}
\]

Code

#include <cstdio>
#include <cstring> const int N = 20000002, mod = 20170408;
int n, m, p, pr[N], np[N], tot, f[102], g[102]; struct Matrix {
int mat[102][102];
Matrix(){ memset(mat, 0, sizeof mat); }
Matrix operator * (const Matrix a) const {
Matrix b;
for (int i = 1; i <= p; ++i)
for (int j = 1; j <= p; ++j)
for (int k = 1; k <= p; ++k)
b.mat[i][j] = (b.mat[i][j] + 1LL * a.mat[i][k] * mat[k][j]) % mod;
return b;
}
} unit, a, b;
void sieve() {
np[1] = 1;
for (int i = 2; i <= m; ++i) {
if (!np[i]) pr[++tot] = i;
for (int j = 1; j <= tot && i * pr[j] <= m; ++j) {
np[i * pr[j]] = 1;
if (i % pr[j] == 0) break;
}
}
}
int ksm(Matrix a, int b) {
Matrix res = unit;
for (; b; b >>= 1, a = a * a)
if (b & 1) res = res * a;
return res.mat[1][1];
}
int main() {
scanf("%d%d%d", &n, &m, &p);
sieve();
for (int i = 1; i <= p; ++i) unit.mat[i][i] = 1;
for (int i = 1; i <= m; ++i) ++f[i % p];
for (int i = 1; i <= m; ++i) if (np[i]) ++g[i % p];
for (int i = 1; i <= p; ++i) {
int k = 1;
for (int j = i - 1; j >= 0; --j, ++k) a.mat[i][k] = f[j], b.mat[i][k] = g[j];
for (int j = p - 1; j >= i; --j, ++k) a.mat[i][k] = f[j], b.mat[i][k] = g[j];
}
printf("%d\n", (ksm(a, n) - ksm(b, n) + mod) % mod);
return 0;
}

[BZOJ 4818] [SDOI 2017] 序列计数的更多相关文章

  1. [BZOJ 4818/LuoguP3702][SDOI2017] 序列计数 (矩阵加速DP)

    题面: 传送门:https://www.lydsy.com/JudgeOnline/problem.php?id=4818 Solution 看到这道题,我们不妨先考虑一下20分怎么搞 想到暴力,本蒟 ...

  2. [SDOI 2017] 序列计数

    [题目链接] https://www.lydsy.com/JudgeOnline/problem.php?id=4818 [算法] 考虑容斥 , 用有至少有一个质数的合法序列数 - 没有质数的合法序列 ...

  3. [BZOJ 3992] [SDOI 2015] 序列统计(DP+原根+NTT)

    [BZOJ 3992] [SDOI 2015] 序列统计(DP+原根+NTT) 题面 小C有一个集合S,里面的元素都是小于质数M的非负整数.他用程序编写了一个数列生成器,可以生成一个长度为N的数列,数 ...

  4. BZOJ 3992 [SDOI 2015] 序列统计 解题报告

    这个题最暴力的搞法就是这样的: 设 $Dp[i][j]$ 为前 $i$ 个数乘积为 $j$ 的方案数. 转移的话就不多说了哈... 当前复杂度 $O(nm^2)$ 注意到,$M$ 是个质数,就说明 $ ...

  5. [BZOJ 3992] [SDOI 2015] 序列统计

    Description 传送门 Solution [一] 设 \(f[i][j]\) 表示前 \(i\) 个数的乘积在模 \(p\) 意义下等于 \(j\) 的方案数,有 \[ f[i][j]=\su ...

  6. [BZOJ 4817] [SDOI 2017] 树点涂色

    Description Bob有一棵 \(n\) 个点的有根树,其中 \(1\) 号点是根节点.Bob在每个点上涂了颜色,并且每个点上的颜色不同. 定义一条路径的权值是:这条路径上的点(包括起点和终点 ...

  7. [BZOJ 4819] [SDOI 2017] 新生舞会

    Description 学校组织了一次新生舞会,Cathy作为经验丰富的老学姐,负责为同学们安排舞伴. 有 \(n\) 个男生和 \(n\) 个女生参加舞会买一个男生和一个女生一起跳舞,互为舞伴. C ...

  8. 【BZOJ 4818】 4818: [Sdoi2017]序列计数 (矩阵乘法、容斥计数)

    4818: [Sdoi2017]序列计数 Time Limit: 30 Sec  Memory Limit: 128 MBSubmit: 560  Solved: 359 Description Al ...

  9. BZOJ4818 序列计数

    4818: [Sdoi2017]序列计数 Time Limit: 30 Sec  Memory Limit: 128 MB Description Alice想要得到一个长度为n的序列,序列中的数都是 ...

随机推荐

  1. ServiceHub.DataWarehouseHost.exe内存泄漏问题的处理

    Visual Studio 2017的15.2版本在debug应用程序时,ServiceHub.DataWarehouseHost.exe会出现严重的内存泄漏的问题,一个小时左右,内存耗了将近8GB. ...

  2. 基础环境系列:Apache2.4.37

    一.安装 进入官网http://www.apache.org/,滑至最下方,排名第一的HTTP Server就是我们需要的. 当前时间的最新版本是2.4.37.呃……并没有msi版本,我们选择最后一个 ...

  3. Hadoop Yarn框架详细解析

    在说Hadoop Yarn之前,我们先来看看Yarn是怎样出现的.在古老的Hadoop1.0中,MapReduce的JobTracker负责了太多的工作,包括资源调度,管理众多的TaskTracker ...

  4. 20181225-Linux Shell Bash环境下自动化创建ssh互信脚本

    20181225-Linux Shell Bash环境下自动化创建ssh互信脚本 1. 我的Blog 博客园 https://www.cnblogs.com/piggybaba/ 个人网站 http: ...

  5. Python生成器、推导式之前襟后裾

    生成器 函数体内有yield选项的就是生成器,生成器的本质是迭代器,由于函数结构和生成器结构类似,可以通过调用来判断是函数还是生成器,如下: def fun(): yield "我是生成器& ...

  6. 【原】Java学习笔记022 - 字符串

    package cn.temptation; public class Sample01 { public static void main(String[] args) { // 字符串 // 定义 ...

  7. Saltstack_使用指南06_远程执行-指定目标

    1. 主机规划 Targeting Minions文档 https://docs.saltstack.com/en/latest/contents.html 另请参见:自动化运维神器之saltstac ...

  8. eclipse中跳转到其它函数方法后如何快速返回原处

    快捷键 ctrl + 鼠标左键:跳转到引用的方法 alt + left :从所跳转到引用的方法返回原方法 alt + right:从原处返回到引用的方法

  9. .NET ORM框架之NHibernate

    这段时间一直使用NHibernate,今天抽空总结一下. 1.什么是NHibernate? NHibernate是一个面向.NET环境的对象/关系数据库映射工具.对象/关系数据库映射(object/r ...

  10. kunbernetes-快速入门

    1.入门概述 本文以在容器云上部署一个nexus3应用为例,通过通过一步步的操作,帮助用户快速的对Kubernetes有一个快速和整体的认识.通过快速入门,可以提供如下知识内容: 在集群中部署一个容器 ...