poj3233

来源:互联网 发布:java开源考勤系统 编辑:程序博客网 时间:2024/06/07 02:29

题目链接:

题目大意:


思路:

Sk=A+ASn-1

所以

(A  Sk-1)* (E   E  )=(A Sk)

                    (0    A)


(A Sk)=(A  A)*(E  E)^(n-1)=(A  0)(E  E)^(n)

                                (0  A)                          (0  A)


既然矩阵递推式出来了,就容易写了,矩阵里套矩阵就是对里面的数组处理时注意下

之前想搞个矩阵套矩阵的模板 搞了半天还不行,还是老老实实的把里面数组开大点,又方便效率又高

#include <cstdio>#include <cstring>#include <cmath>#include <iostream>using namespace std;#define ll long long#define N 150ll mod;ll n,k,m;struct Matrix{    ll r,c;    ll m[N][N];    Matrix(){}    Matrix(ll r,ll c):r(r),c(c){}    Matrix operator *(const Matrix& B)//乘法    {        Matrix T(r,B.c);        for(int i=1;i<=T.r;i++)        {            for(int j=1;j<=T.c;j++)            {                ll tt = 0;                for(int k=1;k<=c;k++)                    tt +=( m[i][k]*B.m[k][j]) % mod;                T.m[i][j] = tt % mod;            }        }        return T;    }Matrix operator =(const Matrix& B)//复制    {        for(int i=1;i<=r;i++)        {            for(int j=1;j<=c;j++)            {                m[i][j] = B.m[i][j];            }        }    }    Matrix operator +(const Matrix& B)//加法    {        for(int i=1;i<=r;i++)        {            for(int j=1;j<=c;j++)            {                m[i][j]+= B.m[i][j];            }        }    }    Matrix Unit(ll h) // 对角线矩阵    {        Matrix T(h,h);        memset(T.m,0,sizeof(T.m));        for(int i=1;i<=h;i++)            T.m[i][i] = 1;        return T;    }    Matrix Pow(ll n)  //矩阵幂    {        Matrix P = *this,Res = Unit(r);        while(n!=0)        {            if(n&1)                Res =Res*P;            P = P*P;            n >>= 1;        }        return Res;    }    void Print()//输出    {        for(int i=1;i<=r;i++)        {            for(int j=1;j<=c;j++)                printf("%d ",m[i][j]);            printf("\n");        }    }}Single;int main(){while(~scanf("%lld%lld%lld",&n,&k,&mod)){Matrix a(2*n,2*n),b(n,2*n);for(int i=1;i<=n;i++)for(int j=1;j<=n;j++){if(i==j)a.m[i][j]=1;elsea.m[i][j]=0;}for(int i=1;i<=n;i++)for(int j=n+1;j<=2*n;j++){if(i==j-n)a.m[i][j]=1;elsea.m[i][j]=0;b.m[i][j]=0;}for(int i=1+n;i<=2*n;i++)for(int j=1;j<=n;j++){a.m[i][j]=0;}for(int i=n+1;i<=2*n;i++)for(int j=n+1;j<=2*n;j++){scanf("%lld",&a.m[i][j]);b.m[i-n][j-n]=a.m[i][j];}a=a.Pow(k);b=b*a;for(int i=1;i<=n;i++)for(int j=n+1;j<=2*n;j++){printf("%lld%c",b.m[i][j],j==2*n?'\n':' ');}}return 0;}



原创粉丝点击