2022.8.11 闲话

《ぽかぽかの星》

ねえ知ってる
呐 你知道吗
かまくらの中は暖かいんだよ
雪洞之中是如此的温暖
思わず眠れちゃうかもね
或许会不知不觉地睡着呢

ねえ知ってる
呐 你知道吗
雪の夜は静かなんだよ
白雪之夜是如此的宁静
违う星にきたみたいだ
就像来到了另一个星球一样

すぐに転んじゃうけど
虽然不小心摔倒了
ぽかぽかのココアでがんばろう
喝上一口暖暖的可可 继续加油吧
今日はそれがいいよね
今天就那样结束吧
故郷でも旅人でも
故乡和旅客
あかりを灯す
都点亮了灯火
美しいのさ笑うも泣くもその全てを
真是美丽啊 就让我把在今天回想起来的
振り返るのは今日くらいだから
一切欢笑与泪水
赠るよ
都送给你吧
らららぼくらが歌えば
啦啦啦 我们的歌声
きみに届くかい
能否传达给你呢
らららぼくらの轨迹を
啦啦啦 我们的轨迹
またいつか思い出せますように
希望有一天能再次回想起来

ねぇ闻いてる
呐 你有在听吗
また退屈になっちゃうんだよ
又变得无聊了呢
氷が溶けてしまえば
若是冰雪融化掉的话

すぐに転んじゃうけど
虽然不小心摔倒了
ふかふかのコートで平気だぞ
不过穿着松软的大衣也没事的哦
みんなそれでいいのに
明明大家那样就好了
何故かいつもひとりになると寂しくなる
为什么总是独自一人便感到寂寞呢

美しいとは笑うことだけじゃないんだろう
所谓美丽并不只是微笑哦
覚えておこう道标となる时まで
直到化作路标为止,请牢记吧
らららぼくらが描けば
啦啦啦 我们所描绘的景色
きみに届くかい
能否传达给你呢
らららぼくらの足迹
啦啦啦 我们留下的脚印
また明日消えてしまうけど
到了明天会再一次消散
消えてしまうけれど
虽然会再一次消散

不思议な话なんだよ
真是不可思议啊
几年経てば
若干年后
また见えるようになるのさ
会再次变得清晰可见
风になる言叶と一绪に
与幻化成风的话语一同

そしたらまた思い出そうよ
若是那样的话就再次想起来吧
この寒い日を
这寒冷的冬日
転んだ後に気付くものよ ぽかぽかの星
摔倒之后发现的 暖暖的星
それで良いのさどこにも
那样就足够了呀
完璧な人なんて居ないのだ
这世上哪里都找不到完美的人啊
また歌おうこんな雪の夜に
在这白雪之夜 再次歌唱吧

矩阵乘法

矩阵乘法与矩阵快速幂

矩阵乘法:\(A_{n\times m}\)\(B_{m\times k}\) 相乘得到矩阵 \(C_{n\times k}\)

\[C_{ij}=\sum_{p=1}^mA_{ip}B_{pj} \]

容易验证矩阵乘法有结合律(但是没有交换律),于是矩阵之幂可以快速幂计算 .

矩阵乘法的一些常数优化:

  • 循环 ikj(利用 CPU Cache).
  • 分块(利用 CPU Cache).
  • 取模优化 .
  • 如果元素为 0 直接跳出(稀疏矩阵).

矩阵乘法的一些正经优化:

  • Strassen 算法,\(O(n^{\log_27})\)(这个有点用,后面皆为扯淡) .
  • Laser 方法:\(O(n^{2.522})\) .
  • Alman 和 Vassilevska Williams 的方法:\(O(n^{2.3728596})\) .

目前人们还未能得知矩阵乘法是否有 \(O(n^2\operatorname{polylog}(n))\) 的算法(01 矩阵在忽略 polylog 因子的情况下和一般矩阵是等价的).


广告:知识落差限制想象力(密码是学校提高 OJ 的 IP),切题的大概是 Det Query I .


Walk

给一个 \(n\) 点无权图,问长度为 \(k\) 的路径有多少条 .

\(n\le 50\)\(k\le 10^{18}\) .

令原图邻接矩阵为 \(G\) .

考虑 DP,\(dp_{u,v,k}\)\(u\to v\) 长度为 \(k\) 的路径 .

显而易见

\[dp_{u,v,k}=\sum_{w=1}^mdp_{u,w,k-1}G_{w,v} \]

可以发现矩阵乘法形式:\(dp_k=dp_{k-1}\cdot G\) .

于是 \(dp_k=G^k\),矩阵快速幂计算,\(O(n^3\log k)\) .

最后把所有 DP 值加起来即可 .


Brute Force

给一张 \(n\) 个点带权有向图,问至少走多少条边使得边权和不小于给定常数 \(M\) .

\(n\le 100\)\(m\le 10^{18}\) .

令原图邻接矩阵为 \(G\) .

DP,令 \(dp_{u,v,k}\) 表示 \(u\to v\) 长度为 \(k\) 的边权和最大值,则

\[dp_{u,v,k}=\max_{w\in[1,m]}\{dp_{u,w,k-1}+G_{w,v}\} \]

显而易见有结合律(发现很多人不会代入定义求解).

于是快速幂优化即可 .

然后是问至少走多少条边,二分 \(O(n\log^2 m)\),倍增 \(O(n\log m)\) .


杰杰的女性朋友

一个神奇的图,每个点 \(u\)\(k\) 个入点权 \(in_{u, 1\dots k}\)\(k\) 个出点权 \(out_{u,1\dots k}\) .

任意两点 \(u,v\) 间路径条数为

\[\sum_{i=1}^nin_{u,i}out_{u,i} \]

多组询问,每次询问由三元组 \((u,v,d)\) 构成,询问从 \(u\) 城市通过不超过 \(d\) 条道路到达 \(v\) 城市的方案数,对 \(10^9+7\) 取模 .

\(n\le 1000\)\(k\le 20\)\(m\le 50\) .

设入点权和出点权矩阵分别为 \(I,O\),则路径条数矩阵为 \(G=OI^{\sf T}\) .

则对于每个询问我们就是要求 \(G^d_{u,v}\),可以发现:

\[G_{u,v}=(OI^{\sf T})^d=O\cdot (I^{\sf T}O)^{d-1}\cdot I^{\sf T} \]

\(OI^{\sf T}\)\(n\times n\) 矩阵,然而 \(I^{\sf T}O\)\(k\times k\) 矩阵,\(O(k^3\log d)\) 显然可以轻松求 .

然而这个是不超过 \(d\) 条,所以我们要求的其实是 \(\displaystyle\sum_{i=1}^{d-1}(I^{\sf T}O)^i\),这个用等比矩阵求和就可以 \(O(k^3\log d)\) 解决 .

具体的,单点暴力快速幂,\(d\) 按奇偶性分治,详见 POJ3233 Matrix Power Series .

问题被 \(O((n+k)k^2\log d)\) 解决 .


No Matrix Power Series

给一个 \(n\) 点无权图,问长度不大于 \(k\) 的路径有多少条 .

\(n\le 50\)\(k\le 10^{18}\) .

给每个结点加一个权值为 \(1\) 的自环,就相当于可以停顿了,于是就变成 Walk .

时间复杂度 \(O(n^3\log k)\) .


美食家

给定一张有向图,\(n\) 个顶点,\(m\) 条边。第 \(i\) 条边从 \(u_i\)​ 到 \(v_i\)​,用时 \(w_i\)​ . 每一个点 \(i\) 有点权 \(c_i\),走到点 \(i\) 可以得到 \(c_i\)​ 的价值 .

\(k\) 个附加元素,第 \(i\) 个附加元素有三个参数:\((t_i, x_i, y_i)\) . 表示当恰好在 \(t_i\)​ 时间点到达顶点 \(x_i\)​ 时,可以得到 \(y_i\)​ 的额外价值 .

初始时间为 \(0\),从起点 \(1\) 开始,走一个回到 \(1\) 的有向环,耗时恰好为 \(T\) . 最终得到的价值为所有经过的点的价值和 .

求最大的最终价值和 .

\(n\le 50\)\(m\le 501\)\(T\le 10^9\)\(w_i\le 5\) .

如果没有附加就直接矩阵快速幂即可,\(w\) 非常小可以拆点 .

有附加考虑按附加分成若干块,分别快速幂,然后加上附加再算 .

快速幂因为要算很多次所以可以倍增 & 杰杰的女性朋友优化一下,\(O(n^2(n+k)\log T)\) .

或者考虑矩阵套矩阵也行 .


沼泽鳄鱼

给一个有 \(n\) 个点,\(m\) 条边的无向图 ,其中有 \(F\) 只鳄鱼以 \(T\) 个点 \(P_{0\dots T-1}\) 为周期运动 . 求从 \(s\) 出发到 \(t\) 恰走 \(k\) 步每步不碰到鳄鱼的方案数 .

\(n\le 50\)\(k\le 2\times 10^9\)\(F\le 20\)\(2\le T\le 4\) .

显而易见鳄鱼行进周期为 \(\operatorname{lcm}(2,3,4)=12\),于是开 12 个矩阵分别快速幂计算,最后合并即可 .

时间复杂度 \(O(F+n^3\log k)\) .


组合数问题

\(n,p,k,r\),求

\[\sum_{i=0}^{\infty}\dbinom{nk}{ik+r} \]

\(p\) 取模的结果 .

\(1 \leq n \leq 10^9\),$ 0 \leq r < k \leq 50$,\(2 \leq p \leq 2^{30} - 1\) .

注意到对组合数作 \(k\) 次展开(代那个递推式)可以得到一个引理

Lemma

\[\dbinom nm=\sum_{i=0}^k\dbinom{n-k}{m-i}\dbinom ki \]

\(k\) 为任意整数 .

\[\begin{aligned}A_{n,r}&=\sum_{i=0}^{\infty}\dbinom{nk}{ik+r}\\&=\sum_{i=0}^{\infty}\sum_{j=0}^k\dbinom{(n-1)k}{ik+r-j}\dbinom kj\\&=\sum_{j=0}^k\sum_{i=0}^{\infty}\dbinom{(n-1)k}{ik+r-j}\dbinom kj\\&=\sum_{j=0}^k\dbinom kj\sum_{i=0}^{\infty}\dbinom{(n-1)k}{ik+r-j}\\&=\sum_{j=0}^k\dbinom kjA_{n-1,r-j}\end{aligned} \]

矩阵快速幂优化即可,时间复杂度 \(O(k^3\log n)\) .


So Easy!

给四个正整数 \(a,b,n,m\),求:

\[S_n=\lceil(a+\sqrt b)^n\rceil\bmod m \]

\(0<a,m<2^{15}\)\(0<b,n<2^{31}\)\((a-1)^2<b<a^2\) .

\(A_n=(a+\sqrt b)^n\)\(B_n=(a-\sqrt b)^n\) .

因为 \(A_n,B_n\) 共轭,故 \(C_n=A_n+B_n\) 是整数 .

又因 \((a-1)^2<b<a^2\),故 \(0<a-\sqrt b<1\),即 \(0<(a-\sqrt b)^n<1\) .

从而 \(B_n<1\),也即 \(C_n=\lceil A_n\rceil\) .

\(S_n=C_n\bmod m\),我们考虑如何求 \(C_n\) .

注意到:

\[\begin{aligned}C_n((a+\sqrt b)+(a-\sqrt b))&=((a+\sqrt b)^n+(a-\sqrt b)^n)\cdot((a+\sqrt b)+(a-\sqrt b))\\&=(a+\sqrt b)^{n+1}+(a-\sqrt b)^{n+1}+(a-\sqrt b)^n(a+\sqrt b)+(a+\sqrt b)^n(a-\sqrt b)\\&=C_{n+1}+(a^2-b)(a+\sqrt b)^{n-1}+(a^2-b)(a-\sqrt b)^{n-1}\\&=C_{n+1}+(a^2-b)C_{n-1}\end{aligned} \]

可以化为 \(C_{n+1}=2a\cdot C_n-(a^2-b)C_{n-1}\) .

显然可以矩阵快速幂优化,大概就是:

\[\begin{bmatrix}C_{n+1}\\C_n\end{bmatrix}=\begin{bmatrix}2a&-a^2+b\\1&0\end{bmatrix}\begin{bmatrix}C_n\\C_{n-1}\end{bmatrix} \]

然后这题就被 \(O(\log n)\) 解决了 .

可能有更优秀做法?


GT 文本生成器

生成一个长度为 \(n\),字符集为 \(\Sigma\) 的字符串 \(S\) .

给定若干模式串 \(s_{1\dots m}\),要求 \(S\) 中不能有任何一个子串为模式串 .

问字符串 \(S\) 的个数 .

答案对 \(P\) 取模,\(P\) 不超过 \(2^{31}\) .

\(n\le 10^9\)\(m\le 20\)\(\sum|s|\le 20\) .

首先建出模式串的 AC 自动机(不妨记转移函数为 \(trans\)) .

考虑 DP,令 \(dp_{i,j}\) 表示串长为 \(i\),在 AC 自动机上走到编号为 \(j\) 的节点的合法串个数 .

则在 AC 自动机上走一步即可完成转移:

\[dp_{i+1, trans(j, c)} = \sum dp_{i,j}\qquad (c\in\Sigma) \]

暴力 DP,时间复杂度 \(O(|\Sigma|n\sum|s|)\) .

然而我们发现 \(i\) 这个玩意和内层转移几乎没关系,只是为了保证转移顺序 .

也就是说这玩意相当于进行了 \(i\) 次内层转移,\(i\) 一维枚举根本没用 .

所以我们构建出内层转移矩阵,然后快速幂即可 .

设 AC 自动机大小为 \(c\),则 DP 部分时间复杂度为 \(O(c^3\log n)\) .

矩阵表达操作

这个感觉非常的 simple,给俩例题意思意思得了 .

这样的题还是挺多的,但是短时间找不过来 QwQ,可以做一下 Simple DS I(知识落差限制想象力).

Addition Robot

给出一个长度为 \(n\),只含有大写字母 \(\tt A\)\(\tt B\) 的字符串 \(S=S_1S_2S_3...S_n\),定义如下函数 \(f(L,R,A,B)\)

function f(L, R, A, B):
	FOR i from L to R
		if S[i] = 'A'
			A = A + B
		else
			B = A + B
	return (A, B)

给出初始字符串 \(S\)\(q\) 次操作:

  • 1 L R:将 \(S_L,S_{L+1},...,S_{R-1},S_r\) 取反(A 变为 B,B 变为 A) .
  • 2 L R A B:输出函数调用 \(f(L,R,A,B)\) 的结果,对 \(10^9+7\) 取模 .

\(1\le n,q\le 10^5\) .

这个神秘 \(A=A+B\)\(B=A+B\) 直接哇咔咔矩阵维护 .

\(A,B\) 翻转可以直接交换矩阵中的元素,总时间复杂度 \(O(q\log n)\) .


树上询问

维护一棵 \(n\) 个节点的树,根为 \(1\) 号节点。每个节点有两个权值 \(k,t\),初始均为 \(0\) . \(q\) 次操作:

  • \(u\) 到根的路径上所有点的 \(k_i\gets k_i+d\) .
  • \(u\) 到根的路径上所有点的 \(t_i\gets t_i+d\cdot k-i\) .
  • 查询 \(u\) 的权值 \(t_u\) .

\(n,q\le 10^5\)\(|d|\le 10\) .

维护列向量 \([k\quad t\quad 1]^{\sf T}\) 即可轻松转移,\(O(q\log n)\) .


如果觉得非常水可以试用矩阵描述一下 segment tree beats!

归约矩阵乘法

举个例子:

Count a tree II

给一棵树,每个节点有一个颜色,若干次询问求树上两个节点路径上的节点的颜色种类数 .

求一个复杂度下界 .

我们假定这个题有一个做法,那么对于两个 \(\sqrt{n/2}\times\sqrt{n/2}\) 的 01 矩阵 \(A,B\)\(C=AB\) .

我们考虑构造下面一种情况:

一棵树,从 \(root\) 挂下来 \(2\sqrt{n/2}\) ​条链,分为前半部分和后半部分,每部分 \(\sqrt{n/2}\) 条 .

如果 \(A_{i,k} = 1\) 那么就在前半部分的第 \(i\) 条链上挂一个颜色为 \(k\) 的节点,若 \(B_{k,j}=1\) 则在后半部分第 \(j\) 条链上挂一个颜色为 \(j\) 的节点 .

\(root\) 的话就随便搞一个大于 \(\sqrt {n/2}\) ​的颜色即可 .

然后对于 \(C_{i,j}\),其实就是 \(\displaystyle\sum_{k=1}^n[A_{i,k}=1][B_{k,j}=1]\),也就是有多少种颜色 \(k\),使得在前半部分的第 \(i\) 条链中出现且在后半部分的第 \(j\) 条链中出现,那么 \(C_{i,j}\) 就是前半部分的第 \(i\) 条链节点数 + 后半部分的第 \(j\) 条链节点数 + 1 - 两条链链底之间的路径的颜色数 .

那么构造 \(O(n)\) 个询问,每次问任意的一个前半部分的链链底到任意的一个后半部分的链链底的颜色数就行了 .

也就是说把 01 矩乘归约到 COT2 了,于是 COT2 不弱于 01 矩乘,这样就可以得到下界了 .

线性方程组

定义与求解

一组未知数 \(\{x_n\}\),方程:

\[\begin{cases}x_1a_{1,1}+x_2a_{1,2}+\cdots+x_na_{1,n}&=b_1\\x_1a_{2,1}+x_2a_{2,2}+\cdots+x_na_{2,n}&=b_2\\\cdots\\x_1a_{m,1}+x_2a_{m,2}+\cdots+x_na_{m,n}&=b_n\end{cases} \]

矩阵形式:

\[\begin{bmatrix}x_1\\x_2\\\vdots\\x_n\end{bmatrix}\begin{bmatrix}a_{1,1}&a_{1,2}&\cdots&a_{1,m}\\a_{2,1}&a_{2,2}&\cdots&a_{2,m}\\\vdots&\vdots&\ddots&\vdots\\a_{n,1}&a_{n,2}&\cdots&a_{n,m}\end{bmatrix}=\begin{bmatrix}b_1\\b_2\\\vdots\\b_n\end{bmatrix} \]

这就是线性方程组 .


Gauss 消元:一行一行消成上三角,消完回代 .

Gauss Jordan 消元:消成每一行都变成只有一项有系数,这样可以规避回代 .

以上都是 \(O(n^3)\) 算法,LU 分解和求逆做法感觉没用 .


Barracuda

\(n\) 个三角形,每个三角形 \(i\) 有一个质量 \(g_i\) .

进行了 \(n + 1\) 次称量,恰有一次有误 .

三角形质量要求满足:

  • 最重的三角形只有一个 .
  • 不存在重量不确定的三角形 .
  • 所有三角形的重量均为正整数 .

问最重三角形的编号,保证解数量不大于 1 .

小三角形的重量不大于 \(100\)\(1\le m \le n\le 100\),无解输出 illegal .

枚举哪次有问题,暴力高消即可,\(O(n^4)\) .


球形空间产生器

一个 \(n\) 维球体,知道球面上 \(n+1\) 个点的坐标,求球心 .

\(1\le n\le 10\) .

设球心坐标为 \((r_1,r_2,\cdots,r_n)\),则:

\[\begin{aligned}\forall i:&\sum (r_i-x_{k,i})^2=R\\ \forall i:&\sum r_i^2-2\sum r_ix_{k,i}+\sum x_{k,i}^2=R\\ \forall i:&2\sum r_ix_{k,i}=\sum x_{k,i}^2-c\\ \forall i:&\sum 2(x_{p,i}-x_{q,i})r_i = \sum (x_{p,i}^2-x_{q,i}^2)\end{aligned}\]

列方程组暴力消元解即可,\(O(n^3)\) .

(上面那个意识流式子是我从 意识流博 里粘的,看不懂的话建议自己推一下)


XOR 和路径

给一个带权图,从 \(1\) 号节点开始,均匀随机选择与当前节点相邻接的某条边,并沿这条边走到下一个节点,重复这个过程,直到走到 \(n\) 号节点为止,得到一条从 \(1\)\(n\) 的路径,求路径边权异或和期望 .

\(2\le n\le 100\)\(m\le 10^4\),边权不大于 \(10^9\) .

由期望线性性,xor 可以按位考虑,于是我们对按位处理 .

\(dp_u\) 表示从 \(u\)\(n\) 路径 xor 和为 \(1\) 的概率,于是

\[dp_u=\dfrac1{\deg u}\left(\sum_{val(u,v)=0}(1-dp_v)+\sum_{val(u,v)=1}dp_v\right) \]

由于可能有后效性,于是考虑 Gauss 消元 .

做完了,注意重边自环的影响,时间复杂度 \(O(wn^3)\),其中 \(w\) 是边权在二进制中的位数 .

基于消元的矩阵基本操作

行列式求值

给一个矩阵 \(A\),求 \(\det(A)\bmod p\) .

其中 \(\displaystyle\det(A)=\sum_{\pi}(-1)^{\tau(\pi)}\prod_{i=1}^na_{i,p_i}\)\(\pi\) 是一个排列,\(\tau(\pi)\) 是其逆序数 .

\(n\le 600\)\(p\le 10^9+7\) .

Algorithm 1. 我会暴力!\(O(n!)\) 轻松跑过~

Algorithm 2. 根据众所周知的线性代数知识我们用 Gauss 消元的变换化成上三角行列式值不变 .

然而 \(a_{i,i}\)​ 在模 \(p\) 意义下不一定有逆元 . 考虑到可以任意相减,这个性质和辗转相除法很相似,可以考虑对两行进行辗转相除,这样一定可以消掉某行第 \(i\) 列 .

时间复杂度 \(O(n^3\log p)\),你这跑得还没 \(O(n!)\) 快呢!

Algorithm 3. 实际上根本不是 \(O(n^3\log p)\),每次做两次消元 \(a_{i,i}\)​ 至少会变为原来的一半,而这个势能是不会上升的,均摊下去复杂度为 \(O(n^2(n+\log p))\),可以通过 .


矩阵求逆

求一个方阵 \(A_{n\times n}\) 的逆矩阵 \(A^{-1}\),对 \(10^9+7\) 取模 .

\(n\le 400\) .

因为

\[A^{-1}[A\ I]=[I\ A^{-1}] \]

所以 Gauss Jordan 消元 \(A^{-1}[A\ I]\) 即可(因为 Gauss Jordan 会把 \(A\) 消成 \(I\)).

时间复杂度 \(O(n^3)\) .


如果觉得太水了可以做一下 Det Query II(知识落差限制想象力).

Tip.

Cramer's Rule

对于线性方程组

\[\begin{bmatrix}x_1\\x_2\\\vdots\\x_n\end{bmatrix}\begin{bmatrix}a_{1,1}&a_{1,2}&\cdots&a_{1,m}\\a_{2,1}&a_{2,2}&\cdots&a_{2,m}\\\vdots&\vdots&\ddots&\vdots\\a_{n,1}&a_{n,2}&\cdots&a_{n,m}\end{bmatrix}=\begin{bmatrix}b_1\\b_2\\\vdots\\b_n\end{bmatrix} \]

若其系数矩阵 \(\displaystyle D = \begin{bmatrix}a_{1,1}&a_{1,2}&\cdots&a_{1,m}\\a_{2,1}&a_{2,2}&\cdots&a_{2,m}\\\vdots&\vdots&\ddots&\vdots\\a_{n,1}&a_{n,2}&\cdots&a_{n,m}\end{bmatrix}\) 可逆(非奇异),即系数行列式 \(\det(D)\neq0\),则线性方程组有唯一解,其解为

\[x_j=\dfrac{\det(D_j)}{\det(D)} \]

其中 \(D_j\) 是把 \(D\) 中第 \(j\) 列元素对应地换成常数项而其余各列保持不变所得到的矩阵 .

band-matrix 消元

band-matrix 就是带状矩阵,消元就交换列就完了 .

Broken robot

\(n\)\(m\) 列的矩阵,有一个博特在 \((x,y)\),每次等概率向左,右,下走或原地不动,但不能走出去,问走到最后一行的期望步数 .

\(n,m\le 10^3\) .

\(dp_{i,j}\) 表示博特在 \((i,j)\) 这个格子期望还需要走多少步才能到最后一行 .

于是:

\[dp_{i,j}=\begin{cases}\frac{1}{4}(dp_{i,j}+dp_{i-1,j}+dp_{i,j-1}+dp_{i,j+1})+1&1<j<m \\ \frac{1}{3}(dp_{i,j}+dp_{i-1,j}+dp_{i,j+1})+1& j=1 \\ \frac{1}{3}(dp_{i,j}+dp_{i-1,j}+dp_{i,j-1})+1&j=m \end{cases} \]

考虑博特只能往下走但是不能往上走,所以第 \(i\) 行的期望只与第 \(i-1\) 行有关,所以只用依次把每行高斯消元即可,这样就是宽度为 2 的 band-matrix,于是就是 \(O(nm)\) 的了 .


Sam 数

相邻两位的数字之差不超过 \(2\) 的数叫做 Sam 数,问 \(k\) 位的 Sam 数有多少个,对 \(10^9+7\) 取模 .

\(k\le 10^{18}\) .

数位 DP,令 \(dp_{i,j}\) 表示 \(i\) 位且第 \(i\) 位为 \(j\) 的方案数,则:

\[dp_{i,j}=\sum_{k=j-2}^{j+2}dp_{i-1,k} \]

注意边界 .

发现这个其实是一个转移矩阵做 \(i\) 遍,于是矩阵快速幂即可 .

发现转移矩阵是 band-matrix,但是大小只有 10,咋做都行吧 .

时间复杂度 \(O(\log k)\) .

当然你可以出个加强版,任意进制的,这样就炫酷了,不过我是不想出了 .

posted @ 2022-08-11 19:05  Jijidawang  阅读(87)  评论(2编辑  收藏  举报
😅​