• P1939 【模板】矩阵加速(数列)


    luogu 传送门
    矩阵乘法快速幂,注意记录过程量;
    还有就是如果前面已经算过了,直接赋值就好了。

    #include<iostream>
    #include<cstdio>
    #include<algorithm>
    #include<string>
    #include<cstring> 
    #define LL long long
    #define MOD 1000000007
    using namespace std;
    LL A[4][4]={
        0,0,0,0,
        0,1,1,0,
        0,0,0,1,
        0,1,0,0,
               };
    LL ans[2][4],B[4][4],C[4][4],bak[4][4],a[109];
    int T;
    struct H{
        LL n;int id;
    }q[109];
    bool cmp(H x,H y){return x.n<y.n;}; 
    void Fast_Pow(LL p)
    {
        p--;
        for(int i=1;i<=3;i++) for(int j=1;j<=3;j++) B[i][j]=C[i][j]=A[i][j];
        while(p)
        {
            if(p%2)//B*C 
            {
                for(int i=1;i<=3;i++) for(int j=1;j<=3;j++) bak[i][j]=B[i][j],B[i][j]=0;
                for(int i=1;i<=3;i++)
                 for(int j=1;j<=3;j++)
                  for(int k=1;k<=3;k++)
                   B[i][j]=(B[i][j]+bak[i][k]*C[k][j]%MOD)%MOD;
            }
            //C*C 
            for(int i=1;i<=3;i++) for(int j=1;j<=3;j++) bak[i][j]=C[i][j],C[i][j]=0;
            for(int i=1;i<=3;i++)
             for(int j=1;j<=3;j++)
              for(int k=1;k<=3;k++)
               C[i][j]=(C[i][j]+bak[i][k]*bak[k][j]%MOD)%MOD;
    
            p/=2;
        }
        for(int i=1;i<=3;i++) bak[1][i]=ans[1][i],ans[1][i]=0;
        ans[1][1]=(bak[1][1]*B[1][1]%MOD+bak[1][2]*B[2][1]%MOD+bak[1][3]*B[3][1]%MOD)%MOD;
        ans[1][2]=(bak[1][1]*B[1][2]%MOD+bak[1][2]*B[2][2]%MOD+bak[1][3]*B[3][2]%MOD)%MOD;
        ans[1][3]=(bak[1][1]*B[1][3]%MOD+bak[1][2]*B[2][3]%MOD+bak[1][3]*B[3][3]%MOD)%MOD; 
    } 
    int main()
    {
        scanf("%d",&T);
        for(int i=1;i<=T;i++)
        {
            scanf("%lld",&q[i].n);
            q[i].id=i;
        }
        ans[1][1]=1,ans[1][2]=1,ans[1][3]=1;
        sort(q+1,q+T+1,cmp);
        for(int i=1;i<=T;i++)
        {
            LL n=q[i].n;
            if(n<=3&&n>=1) {a[q[i].id]=1;continue;}
            if(i==1) Fast_Pow(q[1].n-3); 
            else if(n-q[i-1].n)Fast_Pow(n-q[i-1].n);
            a[q[i].id]=ans[1][1];
        }
        for(int i=1;i<=T;i++) printf("%lld
    ",a[i]);
        return 0;
    }
  • 相关阅读:
    java框架
    MVC编程模式
    java各版本简单对比
    java设计模式
    ES中TF-IDF算法
    es分词器
    java应用零停机,时间索引重建(reindex)
    Spring源码由浅入深系列一 简介
    Spring源代码解析(收藏)
    spring源码读书笔记
  • 原文地址:https://www.cnblogs.com/dfsac/p/7587813.html
Copyright © 2020-2023  润新知