zoukankan      html  css  js  c++  java
  • sdoi<序列计数>

    链接:https://www.luogu.org/problemnew/show/P3702

    题解:

    碰到计数题都要想想容斥

    就跟碰到最大值最小要想想二分一样

    考虑没有一个数是质数

    那就确定了每一个数的取值范围

    那么dp方程很显然

    然后构造矩阵来优化转移

    可以发现每个决策时一样的 所以矩阵可以一列一列的复制

    #include <bits/stdc++.h>
    #pragma comment(linker,"/STACK:102400000,102400000")
    #pragma G++ optimize (“O2”) 
    using namespace std;
    #define ll long long
    const ll maxn= 2e7+100;
    #define mo 20170408
    ll k,n,m;
    bool f[maxn+10];
    struct re{
        ll jz1[110][110],jz2[110][110];
    }a;
    re tmp,c;
    re XX(re x,re y)
    {
        memset(tmp.jz1,0,sizeof(tmp.jz1));
        memset(tmp.jz2,0,sizeof(tmp.jz2));
        for (ll i=0;i<k;i++)
          for (ll j=0;j<k;j++)
            for (ll p=0;p<k;p++)
            {
               tmp.jz1[i][p]=(tmp.jz1[i][p]+x.jz1[i][j]*y.jz1[j][p])%mo;
               tmp.jz2[i][p]=(tmp.jz2[i][p]+x.jz2[i][j]*y.jz2[j][p])%mo;    
            }
        return(tmp);
    }
    re fastpow(ll x)
    {
        cout<<x<<endl;
        if (x==1) return(a);
        c=fastpow(x/2);
        c=XX(c,c);
        if (x%2) c=XX(c,a);
        return c;
    }
    int main()
    {
        freopen("noip.in","r",stdin);
        freopen("noip.out","w",stdout); 
        cin>>n>>m>>k;
        memset(f,1,sizeof(f));
        f[0]=f[1]=0;
        for (ll i=2;i<=maxn;i++)
          if (f[i])
          {
              ll j=2;
              while (j*i<=maxn)
              {
                  f[j*i]=0; j++;
            }
          }
        for (ll i=1;i<=m;i++)
          if (!f[i])
          {
              a.jz1[((-i%k)+k)%k][0]++;
          }
        for (ll i=1;i<k;i++)
        {
            for (ll j=1;j<k;j++)
              a.jz1[j][i]=a.jz1[j-1][i-1];
            a.jz1[0][i]=a.jz1[k-1][i-1];
        }
        for (ll i=1;i<=m;i++)
          a.jz2[((-i%k)+k)%k][0]++;
        for (ll i=1;i<k;i++)
        {
            for (ll j=1;j<k;j++)
              a.jz2[j][i]=a.jz2[j-1][i-1];
            a.jz2[0][i]=a.jz2[k-1][i-1];
        }
        re d=fastpow(n);
        cout<<(d.jz2[0][0]-d.jz1[0][0]+mo)%mo;
        return 0;
    }
  • 相关阅读:
    Android中的回调Callback
    vim编辑器配置及常用命令
    自定义View 和 ViewGroup
    BluetoothClass详解
    BluetoothServerSocket详解
    NSData转换成NSDictionary
    SDWebImage缓存图片的机制(转)
    非ARC和ARC下创建单利模式的宏定义,可以直接套用
    详细例子构建自定义cell
    使用FMDB框架来加载数据库
  • 原文地址:https://www.cnblogs.com/yinwuxiao/p/8481181.html
Copyright © 2011-2022 走看看