C - Recursive sequence (矩陣快速冪)

知識共享許可協議
本作品採用知識共享署名-相同方式共享 4.0 國際許可協議進行許可。

復現的時候一直在推矩陣快速冪的矩陣,可是一直都推不出來。後面才發現我這個sb。把(n+1)^4 的展開寫錯了。導致,沒找到矩陣。其實這個題,本質上很簡單,找到(n+1)^4 和n之間的規律就可以寫出來了。

#include"stdio.h"
#include"string.h"
#include"algorithm"
using namespace std;
typedef long long ll;
const ll mod = 2147493647;
const int N=7;

int T;
ll k,n,m;
ll tmp[N][N];

void multi(ll a[][N],ll b[][N],ll n)
{
    memset(tmp,0,sizeof tmp);
    for(int i=0; i<n; i++)
        for(int j=0; j<n; j++)
            for(int k=0; k<n; k++)
                tmp[i][j]+=((a[i][k] % mod)*(b[k][j] % mod)) % mod;
    for(int i=0; i<n; i++)
        for(int j=0; j<n; j++)
            a[i][j]=tmp[i][j];
}
ll res[N][N];
void Pow(ll a[][N],ll n)
{
    memset(res,0,sizeof res);//n是冪,N是矩陣大小
    for(int i=0; i<N; i++)
        res[i][i]=1;
    while(n)
    {
        if(n&1)
            multi(res,a,N);//res=res*a;複製直接在multi裏面實現了;
        multi(a,a,N);//a=a*a
        n>>=1;
    }
}

ll a[N][N];
void init()
{
    memset(a,0,sizeof(a));
    a[0][0] = 1; a[0][1] = 2; a[0][2] = 1;
    a[1][0] = 1;
    a[2][2] = 1; a[2][3] = 4; a[2][4] = 6; a[2][5] = 4; a[2][6] = 1;
    a[3][3] = 1; a[3][4] = 3; a[3][5] = 3; a[3][6] = 1;
    a[4][4] = 1; a[4][5] = 2; a[4][6] = 1;
    a[5][5] = 1; a[5][6] = 1;
    a[6][6] = 1;
}

int main()
{
    scanf("%d",&T);
    while(T --)
    {
        scanf("%lld%lld%lld",&k,&n,&m);
        if(k <= 2)
        {
            if(k == 1) printf("%lld\n",n);
            else printf("%lld\n",m);
            continue;
        }
        init();
        Pow(a,k - 2);
        ll ans = 0;
        ans = ans + res[0][0] * m % mod; ans %= mod;
        ans = ans + res[0][1] * n % mod; ans %= mod;
        ans = ans + res[0][2] * 81 % mod; ans %= mod;
        ans = ans + res[0][3] * 27 % mod; ans %= mod;
        ans = ans + res[0][4] * 9 % mod; ans %= mod;
        ans = ans + res[0][5] * 3 % mod; ans %= mod;
        ans = ans + res[0][6] % mod; ans %= mod;
        printf("%lld\n",ans);
    }
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章