矩阵,主要用于递推/\(dp\)优化,以及特别的题目。
运算:
注意,矩阵有\(+,-,*,pow\)以及矩阵的逆等运算。本文讨论入门的\(+,-,*,pow\).
对于加法:
\[
\left[
\begin{matrix}
1&3&5\\
2&4&7\\
\end{matrix}
\right]+
\left[
\begin{matrix}
2&9&7\\
12&9&3\\
\end{matrix}
\right]
\]
即为:
\[
\left[
\begin{matrix}
3&12&12\\
14&13&10\\
\end{matrix}
\right]
\]
就是遵循按位相加的原则,减法同理。
注意矩阵的加减法必须是同行数同列数的矩阵。
对于乘法:
定义\(C_{i,j}\)是\(A,B\)两个矩阵乘完之后的矩阵对应的第\(i\)行第\(j\)列的元素。
规定\(A\)为\(P*M\)的矩阵,\(B\)为\(M*Q\)的矩阵。
则有:
\[C_{i,j}=\sum_{k=1}^{M}{A_{i,k}*B_{k,j}}\]
也可以简单理解为,对应行乘以对应列。
矩阵快速幂
就是一个矩阵的乘方。
注意,只有方阵才有乘方,即列数等于行数\((n*n)\)
同样地,若求一个矩阵的\(k\)次方,可以和二进制快速幂一样,重载乘法即可。
注意提到一个概念:矩阵中,和\(1\)一样的存在是谁呢?我们称之为 $单位矩阵 ,就是对角线上都是\(1\),其它位置都是\(0\)的矩阵。
通过矩阵乘法定义会发现,一个矩阵乘以单位矩阵(称之为\(I\))等于它本身。
一个简单的单位矩阵:
\[
\left[
\begin{matrix}
1&0&0\\
0&1&0\\
0&0&1\\
\end{matrix}
\right]
\]
代码实现:
struct matrix{ ll a[4][4]; matrix(){memset(a,0,sizeof(a));} matrix operator*(const matrix&b)const{ matrix res; for(int i=1;i<=2;++i) for(int j=1;j<=2;++j) for(int k=1;k<=2;++k) res.a[i][j]=(res.a[i][j]+a[i][k]*b.a[k][j])%mod; return res; } }base,ans; void qpow(int b){ while(b){ if(b&1)ans=ans*base; base=base*base;b>>=1; } }
待补\(QwQ\)