HDU 4686 Arc of Dream(矩阵快速幂)

来源:互联网 发布:网络信息安全的概念 编辑:程序博客网 时间:2024/05/02 04:59

大意:已知 a0 = A0
ai = ai-1*AX+AY
b0 = B0
bi = bi-1*BX+BY
这里写图片描述
What is the value of AoD(N) modulo 1,000,000,007?

思路:已知an,bn是一个递推式,AoD(n)也是一个递推式,所以试想用一个快速幂解决。那么就应该把a0,b0,ax,ay,bx,by代进去构成一个式子。那么就可以构造矩阵了。因为an,bn,AoD,都需要求所以根据需要构成一个7*7的矩阵。
盗用一下别人的图

那么什么又是最后的答案呢?肯定是构造矩阵连乘后的结果乘以初始值。
(PS:n可能为0,优化一下)

#include<map>#include<cmath>#include<queue>#include<cmath>#include<string>#include<cstdio>#include<stack>#include<iostream>#include<cstring>#include<algorithm>#define inf 0x3f3f3f3f#define eps 1e-8#define ls l,mid,rt<<1#define rs mid+1,rt,rt<<1|1#define LL __int64using namespace std;__int64 mod = 1000000007,MOD = 1000000007,N=7;__int64 a,ax,ay,b,bx,by,n;struct node{    __int64 r[10][10];}q;node matrix_pow(node a,node b){    __int64 i,j,k;    node t;    memset(t.r,0,sizeof(t.r));    for(k = 0;k < 7;++ k){        for(i = 0 ;i < 7;++ i){            for(j = 0;j < 7;++ j){                t.r[i][j] = (t.r[i][j]+ (a.r[i][k]*b.r[k][j]))%mod;            }        }    }    return t;}node so(node q,__int64 m){    __int64 i,j,k;    node tmp;    memset(tmp.r,0,sizeof(tmp.r));    for(i = 0;i < N;++ i )            tmp.r[i][i] = 1;    while(m){        if(m&1)            tmp = matrix_pow(tmp,q);        q = matrix_pow(q,q);        m = m >> 1;    }    __int64 sum = 0;    sum += tmp.r[N-1][0]*(a*b%MOD)%MOD;    sum %= MOD;    sum += tmp.r[N-1][1]*a%MOD;    sum %= MOD;    sum += tmp.r[N-1][2]*b%MOD;    sum %= MOD;    sum += tmp.r[N-1][3]*(ay*by%MOD)%MOD;    sum %= MOD;    sum += tmp.r[N-1][4]*ay%MOD;    sum %= MOD;    sum += tmp.r[N-1][5]*by%MOD;    sum %= MOD;    printf("%I64d\n",sum);}int main(){    __int64 m,k,i,j;    while(~scanf("%I64d",&n)){        scanf("%I64d%I64d%I64d%I64d%I64d%I64d",&a,&ax,&ay,&b,&bx,&by);        memset(q.r,0,sizeof(q.r));        q.r[0][0] = ax*bx%mod;  q.r[0][2] = bx*ay%mod;        q.r[0][1] = ax*by%mod;  q.r[0][3] = 1;        q.r[1][1] = ax%mod; q.r[1][4] = 1;        q.r[2][2] = bx%mod; q.r[2][5] = 1;        q.r[3][3] = 1;q.r[4][4] = 1;        q.r[5][5] = 1;        q.r[6][6] = q.r[6][0] = 1;        q = so(q,n);    }    return 0;}
0 0