FZU 1911 Construct a Matrix(矩阵快速幂+构造)

来源:互联网 发布:java me模拟器 编辑:程序博客网 时间:2024/06/07 00:04

思路:S(n) = S(n-1) + f(n),通过构造矩阵可以求出S(n),主要问题就是构造一个S(n) * S(n)的矩阵满足条件。

自己写一写就能找出构造方法,因为矩阵只包括0,1,-1,那么一个n*n的矩阵,每一行的sum在-n到n之间,又因为-n和n不能同时存在,所以我们可以让每一行的和在-n到n-1之间,一共2*n个数,刚好对应n行,n列,每一行每一列的sum都不相同,然后构造就行了。

#include<cstdio>#include<cstring>using namespace std;const int mod = 1e9 + 7;const int maxn = 1e6 + 10;typedef long long LL;struct Mutrix{    LL a[3][3];    Mutrix(){        memset(a, 0, sizeof a);    }};Mutrix A, B;LL m;void init(){    A.a[0][0] = 1, A.a[0][1] = 1, A.a[0][2] = 1;    B.a[0][0] = 1;    B.a[1][2] = 1;    B.a[2][0] = 1, B.a[2][1] = 1, B.a[2][2] = 1;}Mutrix mul(Mutrix p1, Mutrix p2){    Mutrix s;    for(int i = 0; i < 3; ++i){        for(int k = 0; k < 3; ++k){            for(int j = 0; j < 3; ++j){                s.a[i][j] += p1.a[i][k] * p2.a[k][j] % m;                s.a[i][j] %= m;            }        }    }    return s;}Mutrix quick_mod(Mutrix x, LL y){    Mutrix ret;    for(int i = 0; i < 3; ++i) ret.a[i][i] = 1;    while(y){        if(y & 1) ret = mul(ret, x);        x = mul(x, x);        y >>= 1;    }    return ret;}int a[220][220];int main(){    LL n;    int kase = 0, T;    scanf("%d", &T);    while(T--){        scanf("%I64d%I64d", &n, &m);        init();        LL w = mul(A, quick_mod(B, n - 1)).a[0][0] % m;        printf("Case %d: ", ++kase);        if(w == 0 || w & 1) {            printf("No\n");            continue;        }        else printf("Yes\n");        memset(a, 0, sizeof a);        for(int i = 0; i < w; ++i){            for(int j = 0; j < w; ++j){                if(i < w / 2){                    if(j >= i) a[i][j] = 1;                }                else{                    if(j < i) a[i][j] = -1;                }            }        }        for(int i = 0; i < w; ++i){            for(int j = 0; j < w; ++j){                printf("%d ", a[i][j]);            }            printf("\n");        }    }    return 0;}


原创粉丝点击