BZOJ 4002 有意义的字符串

Posted on 2016-10-17 19:24  ziliuziliu  阅读(126)  评论(0编辑  收藏  举报

WA一下午的原因是矩阵有两个值打反了。。。

#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
#include<cmath>
#define ll unsigned long long
#define mod 7528443412579576937UL
using namespace std;
struct matrix
{
    ll a[3][3];
}p,q;
ll b,d,n;
ll read()
{
    char ch;ll data=0;
    while (ch<'0' || ch>'9') ch=getchar();
    while (ch>='0' && ch<='9')
    {
        data=data*10+ch-'0';
        ch=getchar();
    }
    return data;
}
ll mull(ll a,ll b)
{
    a%=mod;b%=mod;
    ll ans=0,base=b;
    while (a)
    {
        if (a&1) ans=(ans+base)%mod;
        base=(base+base)%mod;
        a>>=1;
    }
    return ans;
}
void get_table()
{
    p.a[1][1]=2;p.a[1][2]=b;
    q.a[1][1]=0;q.a[2][1]=1;q.a[1][2]=(d-b*b)/4;q.a[2][2]=b;
}
matrix mul(matrix a,matrix b)
{
    matrix c;
    for (ll i=0;i<=2;i++)
        for (ll j=0;j<=2;j++)
            c.a[i][j]=0;
    for (ll i=1;i<=2;i++)
        for (ll j=1;j<=2;j++)
            for (ll k=1;k<=2;k++)
                c.a[i][j]=(c.a[i][j]+mull(a.a[i][k],b.a[k][j]))%mod;
    return c;
}
void f_pow(ll y)
{
    matrix base=q;
    while (y)
    {
        if (y&1) p=mul(p,base);
        base=mul(base,base);
            y>>=1;
    }
}
int main()
{
    b=read();d=read();n=read();
    get_table();
    f_pow(n);
    if (b*n==d) printf("%lld\n",p.a[1][1]%mod);
    else if (n%2) printf("%lld\n",p.a[1][1]%mod);
    else printf("%lld\n",(p.a[1][1]-1+mod)%mod);
    return 0;
}