矩阵快速幂
最近学数学学的比较多,矩阵快速幂应该算数学吧。
题目链接
题目大意:
给定\(n\),\(k\),然后给定\(n \times n\)的矩阵A,求\(A^k\)
数据范围:
\(1\le n \le 100,0 \le q \le 10^12,\vert A_{i,j} \vert \le 1000\)
做法就和快速幂没什么区别,把\(k\)进行二进制拆分,然后快速幂模板
我\(k\)开了long long,读入用的%d,一直没看出来,拖了好久[貌似是重构之后发现的]
看到\(k\)的范围,请大家一定记住:
\(1\) \(0\) 年 \(O\) \(I\) 一 场 空 , 不 开 \(l\) \(o\) \(n\) \(g\) \(l\) \(o\) \(n\) \(g\) 见 祖 宗 。
long long re=1;
for(;power;power>>=1,base=base*base){
    if(power&1)re=re*base;//for循环甚至可以压到一行
}
return re;
只不过这里的\(base\)乘不再是一个数,而是一个矩阵,\(mat\)也一样,需要注意的是,在矩阵里\(1\)代表的是单位矩阵,所以注意返回值要初始化成单位矩阵[对角线都是\(1\)].剩下的矩阵乘法就行了
以下是模板
struct Matrix{//结构体
    ll a[N][N];//ll就是long long
    Matrix(){
        memset(a,0,sizeof(a));//一旦定义,初始化为这样
    }
    void scan(){
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                in(a[i][j]);//读入矩阵,n开的全局变量,不需要矩阵里自己存
    }
    void init(){
        for(int i=1;i<=n;i++)
            a[i][i]=1;//init有初始化的意思,这里是单位矩阵初始化
    }
    void print(){
        for(int i=1;i<=n;i++){
            for(int j=1;j<=n;j++)
                out(a[i][j]);//输出
            putchar(10);//10在ASCII码中是换行,32是空格
        }
    }
    Matrix operator * (const Matrix &b)const{//重载乘法为矩阵乘法
        Matrix ret;
        for(int i=1;i<=n;i++)
            for(int j=1;j<=n;j++)
                for(int u=1;u<=n;u++)
                    ret.a[i][j]=(ret.a[i][j]+(a[i][u]*b.a[u][j])%md)%md;//矩阵乘的定义,i行j列的数,是前一个矩阵第i行乘后一个第j列
        return ret;
    }
}mat,base;
主函数:
int main(){
    in(n),in(k);
    base.scan();mat.init();//mat就是ans,base就是底数
    MQP(k);//Matrix Quick Power 矩阵 快速 乘方
    mat.print();//输出
    return 0;
}
    我不想就这样沦陷,迷失在黑夜,我将燃烧这生命,就算再壮烈。

 
                
            
         
         浙公网安备 33010602011771号
浙公网安备 33010602011771号