[CSP-S模拟测试]:涂色游戏(DP+组合数+矩阵快速幂)
题目描述
小$A$和小$B$在做游戏。
他们找到了一个$n$行$m$列呈网格状的画板。小$A$拿出了$p$支不同颜色的画笔,开始在上面涂色。看到小$A$涂好的画板,小$B$觉得颜色太单调了,于是把画板擦干净,希望涂上使它看起来不单调的颜色(当然,每个格子里只能涂一种颜色)。小$B$想知道一共有多少种不单调的涂色方案。我们定义一个涂色方案是不单调的,当且仅当任意相邻两列都出现了至少$q$种颜色。
输入格式
一行四个整数$n,m,p,q$,意义如题中所述。
输出格式
一行一个整数,表示不单调的涂色方案数模$998244353$的值。
样例
样例输入:
2 3 3 3
样例输出:
162
数据范围与提示
对于$20\%$的数据:$n\times m\leqslant 15,q\leqslant p\leqslant 3$
对于另外$20\%$的数据:$n\leqslant 7,m\leqslant 100,p=q=2$
对于另外$30\%$的数据:$n\leqslant 100,m\leqslant 1,000,q\leqslant p\leqslant 100$
对于$100\%$的数据:$n\leqslant 100,m\leqslant {10}^9 ,q\leqslant p\leqslant 100$
题解
首先,明确题意,不能不涂(也是被这个我并没有看出来的条件坑死了……)
静观数据范围,显然是矩阵快速幂。
那么,我们现在思考如何构建转移矩阵。
先把矩阵搁在一边,考虑$DP$,设$f[i][j]$表示对于一列,选到了第$i$行的格子,恰好涂了$j$种颜色的方案数,直接给出式子:
$$f[i][j]=f[i-1][j-1]\times (p-(j-1))+f[i-1][j]\times j$$
前半部分的转移即为又选了一个新的,那么我就要在这么多的颜色中再选一个;后半部分相当于我又从原来的$j$中颜色中选了一种涂在了这里。
那么,我们在设$g[j]$表示对于一列,选了$j$种颜色的方案数,那么根据第二类斯特林数(类比将$n$个有区别的小球放进$m$个没有区别的盒子,每个盒子至少放一个小球),一列中涂上每种$j$元颜色集合的颜色的方案数就是$\frac{g[j]}{C_p^j}$。
那么,我们对于这一列用了$j$元集合,下一列要用$k$元集合,则方案数为:
$$\sum \limits_{x=\max(q,j,k)}^{\min(p,j+k)}C_j^{j+k-x}C_{p-i}^{x-j}$$
解释一下上式,考虑两个极端情况,$\alpha.j\cup k=\varnothing$,$\beta.j\subset k\ or\ k\subset j$,这也是上式的上下线;再来理解组合数,因为$j$和$k$会有交集,所以前一个组合数就是交集,而第二个就是交集以外的。
现在,我们令:
$$trans[j][k]=\frac{g[j]}{C_p^j}\sum \limits_{x=\max(q,j,k)}^{\min(p,j+k)}C_j^{j+k-x}C_{p-i}^{x-j}$$
那么,$dp[i][k]=dp[i-1][j]\times [j][k]$,$dp[1][j]=g[j]$。
这样我们就可以拿到$70$分了。
观察式子,可以用矩阵快速幂快速转移。
时间复杂度:$\Theta(n^3\log m)$。
期望得分:$100$分。
实际得分:$100$分。
代码时刻
#include<bits/stdc++.h>
using namespace std;
const int mod=998244353;
int n,m,p,q;
long long C[1001][1001],g[101][101];
long long wzc[101][101],ans[101][101],flag[101][101];
void matrix1()
{
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
{
flag[i][j]=ans[i][j];
ans[i][j]=0;
}
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
for(int k=1;k<=n;k++)
ans[i][j]=(ans[i][j]+flag[i][k]*wzc[k][j]%mod)%mod;
}
void matrix2()
{
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
{
flag[i][j]=wzc[i][j];
wzc[i][j]=0;
}
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
for(int k=1;k<=n;k++)
wzc[i][j]=(wzc[i][j]+flag[i][k]*flag[k][j]%mod)%mod;
}
void pre_work()
{
g[0][0]=C[0][0]=1;
for(int i=1;i<=100;i++)
{
C[i][0]=ans[i][i]=1;
for(int j=1;j<=i;j++)
C[i][j]=(C[i-1][j]+C[i-1][j-1])%mod;
}
}
int main()
{
scanf("%d%d%d%d",&n,&m,&p,&q);
pre_work();m--;
for(int i=1;i<=n;i++)
for(int j=1;j<=n;j++)
g[i][j]=j*(g[i-1][j]+g[i-1][j-1])%mod;
for(int j=1;j<=p;j++)
for(int k=1;k<=p;k++)
{
for(int x=max(max(q,j),k);x<=min(p,j+k);x++)
wzc[j][k]=(wzc[j][k]+C[j][j+k-x]*C[p-j][x-j]%mod)%mod;
wzc[j][k]=wzc[j][k]*g[n][k]%mod;
}
while(m)
{
if(m&1)matrix1();
matrix2();
m>>=1;
}
for(int i=1;i<=p;i++)
for(int j=1;j<=p;j++)
ans[0][0]=(ans[0][0]+ans[i][j]*C[p][i]%mod*g[n][i]%mod)%mod;
printf("%lld",ans[0][0]);
return 0;
}
rp++
[CSP-S模拟测试]:涂色游戏(DP+组合数+矩阵快速幂)的更多相关文章
- 【POJ2778】DNA Sequence 【AC自动机,dp,矩阵快速幂】
题意 题目给出m(m<=10)个仅仅由A,T,C,G组成的单词(单词长度不超过10),然后给出一个整数n(n<=2000000000),问你用这四个字母组成一个长度为n的长文本,有多少种组 ...
- CF1151F Sonya and Informatics(概率期望,DP,矩阵快速幂)
明明是水题结果没切掉……降智了…… 首先令 $c$ 为序列中 $0$ 的个数,那么排序后序列肯定是前面 $c$ 个 $0$,后面 $n-c$ 个 $1$. 那么就能上 DP 了.(居然卡在这里……) ...
- [CSP-S模拟测试]:长寿花(DP+组合数)
题目描述 庭院里有一棵古树.圣诞节到了,我想给古树做点装饰,给他一个惊喜.他会不会喜欢呢?这棵树可以分为$n$层,第$i$层有$a_i$个防治装饰品的位置,有$m$种颜色的装饰品可供选择.为了能让他喜 ...
- Gym 100952H&&2015 HIAST Collegiate Programming Contest H. Special Palindrome【dp预处理+矩阵快速幂/打表解法】
H. Special Palindrome time limit per test:1 second memory limit per test:64 megabytes input:standard ...
- BZOJ 1444 有趣的游戏(AC自动机+矩阵快速幂)
真的是很有趣的游戏... 对每个单词构建好AC自动机后,由于单词都是相同长度的且不同,所以不会出现互相为子串的形式. 那么我们对AC自动机上的节点构建转移矩阵.对于每个单词末尾的节点.该节点的出边仅仅 ...
- [hdu5411 CRB and Puzzle]DP,矩阵快速幂
题意:给一个有向图,从任意点开始,最多走m步,求形成的图案总数. 思路:令dp[i][j]表示走j步最后到达i的方法数,则dp[i][j]=∑dp[k][j-1],其中k表示可以直接到达i的点,答案= ...
- 51nod 1835 - 完全图 - [dp][组合数公式][快速幂]
题目链接:https://www.51nod.com/onlineJudge/questionCode.html#!problemId=1835 基准时间限制:1 秒 空间限制:131072 KB ...
- bzoj2004 矩阵快速幂优化状压dp
https://www.lydsy.com/JudgeOnline/problem.php?id=2004 以前只会状压dp和矩阵快速幂dp,没想到一道题还能组合起来一起用,算法竞赛真是奥妙重重 小Z ...
- 联赛模拟测试5 涂色游戏 矩阵优化DP
题目描述 分析 定义出\(dp[i][j]\)为第\(i\)列涂\(j\)种颜色的方案数 然后我们要解决几个问题 首先是求出某一列涂恰好\(i\)种颜色的方案数\(d[i]\) 如果没有限制必须涂\( ...
随机推荐
- Docker安装Web前端性能测试工具Sitespeed.io
一.Sitespeed.io概述 1.Sitespeed.io简介 Sitespeed.io:是一款开源的Web性能测试工具,用来衡量Web网站的综合性能,帮助开发和测试人员分析网页的加载速度和渲染性 ...
- 转载 IDEA搭建maven项目详细步骤(解决没有src及其下面的文件)
转载自
- python的前景
最近几年Python编程语言在国内引起不小的轰动,有超越Java之势,本来在美国这个编程语言就是最火的,应用的非常非常的广泛,而Python的整体语言难度来讲又比Java简单的很多.尤其是在运维的应用 ...
- Docker配置远程访问
近来学习Docker部署微服务,需要配置Docker的远程访问,由于实际环境和学习资料有出入,尝试着根据网上搜索的一些相关资料进行配置,未能成功.最终通过自己摸索,成功配置Docker远程访问.现和大 ...
- jsoncpp解析非json串
转自:https://www.cnblogs.com/huojing/articles/5927488.html 由于Jsoncpp解析非法json时,会自动容错成字符类型.对字符类型取下标时,会触发 ...
- 查找idt table 所對應的page table in Linux
#include <linux/kernel.h> #include <linux/module.h> #include <linux/types.h> #incl ...
- k8s<------docker
- L The Digits String(没有写完,有空补)
链接:https://ac.nowcoder.com/acm/contest/338/L来源:牛客网 Consider digits strings with length n, how many d ...
- 最小生成树,Prim算法实现
最小生成树 所谓最小生成树,就是一个图的极小连通子图,它包含原图的所有顶点,并且所有边的权值之和尽可能的小. 首先看看第一个例子,有下面这样一个带权图: 它的最小生成树是什么样子呢?下图绿色加粗的边可 ...
- Go语言_流程控制语句:for、if、else、switch 和 defer
流程控制语句:for.if.else.switch 和 defer 学习如何使用条件.循环.分支和推迟语句来控制代码的流程. Go 作者组编写,Go-zh 小组翻译. https://go-zh.or ...