羅区P1939 [テンプレート]マトリックス(列の数)を加速

羅区P1939 [テンプレート]マトリックス(列の数)を加速

説明

  • [1] = [2] [3] = 1 =

    [X] [X-3] = + [X-1](x> 3)

    モジュロ列N十億七(10 ^ 9 + 7)の項目数の値を見つけます。

入力

  • 最初の行の整数Tは、質問の数を示します。

    次のTライン、各正の整数n。

出力

  • 出力の各行非負整数の答え。

サンプル入力

3
6
8
10

サンプル出力

4
9
19

データサイズ

  • nのデータの30%<= 100。

    nのデータの60%<= 2 * 10 ^ 7。

    データT <= 100、N <= 2 * 10 ^ 9の100%、

ソリューション:

  • 行列は加速します。
  • 水が直接質問を遮断します
#include <iostream>
#include <cstdio>
#include <cstring>
#define mod 1000000007
#define LL long long
using namespace std;

struct Obj
{
    LL m[4][4];
    Obj () {memset(m, 0, sizeof(m));}
};
LL T, n;

Obj mul(Obj a, Obj b)
{
    Obj c;
    for(LL i = 1; i <= 3; i++)
        for(LL j = 1; j <= 3; j++)
            for(LL k = 1; k <= 3; k++)
                c.m[i][j] += (a.m[i][k] % mod * b.m[k][j] % mod) % mod,
                c.m[i][j] %= mod;
    return c;
}

Obj power(Obj a, LL b)
{
    Obj d; d.m[1][1] = d.m[2][2] = d.m[3][3] = 1;
    Obj r = d, base = a;
    while(b)
    {
        if(b & 1) r = mul(r, base);
        base = mul(base, base);
        b >>= 1;
    }
    return r;
}

int main()
{
    cin >> T;
    while(T--)
    {
        cin >> n;
        if(n <= 3) {cout << 1 << endl; continue;}
        Obj t1;
        t1.m[1][1] = t1.m[1][3] = t1.m[2][1] = t1.m[3][2] = 1;
        t1 = power(t1, n - 3);
        Obj t2, ans; t2.m[1][1] = t2.m[2][1] = t2.m[3][1] = 1;
        for(LL i = 1; i <= 3; i++)
            for(LL j = 1; j <= 1; j++)
                for(LL k = 1; k <= 3; k++)
                    ans.m[i][j] += (t1.m[i][k] % mod * t2.m[k][j] % mod) % mod,
                    ans.m[i][j] %= mod;
        cout << ans.m[1][1] << endl;
    }
    return 0;
}

おすすめ

転載: www.cnblogs.com/BigYellowDog/p/11204530.html