[浅谈·矩阵快速幂]

矩阵快速幂
矩阵快速幂实质上将矩阵作为一个整体,用快速幂的思想进行运算
•但要注意三点:
1.十年OI一场空,不开long long见祖宗
2.注意矩阵乘法的顺序,不满足交换律
3.基础矩阵作为快速幂中的  ” 1 ”
 
矩阵快速幂的实际应用有很多种,其中最主要的是矩阵加速数列
回到P1932  如何用矩阵实现加速
设矩阵
|   f(n)   |     它可以表示为  | f(n-1)+f(n-2)  |
|  f(n-1) | (Maxtrix  A)    |  f(n-1)             |(Maxtrix C)
 
可以考虑设一个矩阵 B  使得 B*A=C(顺序性)   (A*B和B*A不同!!!)
•根据矩阵相乘的原理,容易得出这个矩阵为
•| 1 0 |
•| 1 1 |
•因此如果要让f(1) 变成  f(n) ,只需要重复地乘 n 次B矩阵,再取
•矩阵中(1,1)的值即可
•F(n)=f(1)*B^n
 
 
P3390code
#include<iostream>
#include<cstdio>
#define ll long long
#define mod 1000000007 
#include<cstring>
#include<string>
#include<cmath>
using namespace std;
int n;
ll k;
struct Maxtrix{
    ll m[205][205];
}ans,res,IOI;
Maxtrix Mul(Maxtrix A,Maxtrix B)
{
    Maxtrix temp;
    memset(temp.m,0,sizeof(temp.m));
    for(register int i=1;i<=n;i++)
       for(register int j=1;j<=n;j++)
          for(register int k=1;k<=n;k++)
              temp.m[i][j]=(temp.m[i][j]%mod+(A.m[i][k]%mod*B.m[k][j])%mod)%mod;
    return temp;
}
Maxtrix quickPower(Maxtrix a,ll N)
{
    Maxtrix ans;
    for(register int i=1;i<=n;i++) ans.m[i][i]=1;
    while(N)
    {
        if(N&1)
          ans=Mul(ans,a);
          a=Mul(a,a);
          N>>=1;
    }
    return ans;
}
int main()
{
    cin>>n>>k;
    for(register int i=1;i<=n;i++)
        for(register int j=1;j<=n;j++){
            cin>>res.m[i][j];
        }

    IOI=quickPower(res,k);
    for(register int i=1;i<=n;i++)
    {
        for(register int j=1;j<=n;j++)
        {
            printf("%lld ",IOI.m[i][j]%mod);
        }
        printf("\n");
    }
    return 0;
}
posted @ 2018-12-22 21:18  风丨铃  阅读(323)  评论(0编辑  收藏  举报