zoukankan      html  css  js  c++  java
  • [BZOJ4589]Hard Nim

    description

    BZOJ
    题意:(n)堆式子,每堆石子数量为(le m)的质数,对于每一个局面玩(Nim)游戏,求后手必胜的方案数。

    data range

    [nle 10^9,mle 5 imes 10^4 ]

    solution

    直接(FWT)多项式快速幂即可。

    之前写的多项式快速幂一直是(O(mlogmlogn))
    然后在这一道题上(T)了...

    (\%)了一发(yyb)的代码才知道原来可以快速幂的时候可以不用每次(FWT)
    这样就变成(O(m(logm+logn)))的了

    orz 神仙yyb

    Code

    #include<algorithm>
    #include<iostream>
    #include<cstdlib>
    #include<iomanip>
    #include<cstring>
    #include<complex>
    #include<vector>
    #include<cstdio>
    #include<string>
    #include<bitset>
    #include<ctime>
    #include<cmath>
    #include<queue>
    #include<stack>
    #include<map>
    #include<set>
    #define Cpy(x,y) memcpy(x,y,sizeof(x))
    #define Set(x,y) memset(x,y,sizeof(x))
    #define FILE "a"
    #define mp make_pair
    #define pb push_back
    #define RG register
    #define il inline
    using namespace std;
    typedef unsigned long long ull;
    typedef vector<int>VI;
    typedef long long ll;
    typedef double dd;
    const int N=1<<16;
    const int M=1e5+10;
    const int mod=1e9+7;
    const int base=26;
    const dd eps=1e-6;
    const int inf=2147483647;
    const ll INF=1ll<<60;
    const ll P=100000;
    il ll read(){
      RG ll data=0,w=1;RG char ch=getchar();
      while(ch!='-'&&(ch<'0'||ch>'9'))ch=getchar();
      if(ch=='-')w=-1,ch=getchar();
      while(ch<='9'&&ch>='0')data=data*10+ch-48,ch=getchar();
      return data*w;
    }
    
    il void file(){
      srand(time(NULL)+rand());
      freopen(FILE".in","r",stdin);
      freopen(FILE".out","w",stdout);
    }
    
    int pri[N];bool vis[N];
    il void upd(int &a,int b){a+=b;if(a>=mod)a-=mod;}
    il void dec(int &a,int b){if(b)upd(a,mod-b);}
    il void sieve(){
      vis[1]=1;
      for(RG int i=2;i<N;i++){
        if(!vis[i])pri[++pri[0]]=i;
        for(RG int j=1;j<=pri[0]&&1ll*i*pri[j]<N;j++){
          vis[i*pri[j]]=1;if(i%pri[j]==0)break;
        }
      }
    }
    il void FWT_xor(int *a,int n,int opt){
      for(RG int i=1,x,y,inv2=(mod+1)/2;i<n;i<<=1)
        for(RG int j=0,p=i<<1;j<n;j+=p)
          for(RG int k=0;k<i;k++){
    	x=a[j+k];y=a[i+j+k];a[i+j+k]=x;
    	upd(a[j+k],y);dec(a[i+j+k],y);
    	if(opt==-1)a[j+k]=1ll*a[j+k]*inv2%mod,a[i+j+k]=1ll*a[i+j+k]*inv2%mod;
          }
    }
    int f[N],g[N];
    
    int main()
    {
      sieve();RG int n,m;
      while(scanf("%d%d",&n,&m)!=EOF){
        memset(f,0,sizeof(f));memset(g,0,sizeof(g));f[0]=1;
        for(RG int i=1;pri[i]<=m&&i<=pri[0];i++)g[pri[i]]=1;
        FWT_xor(f,N,1);FWT_xor(g,N,1);
        while(n){
          if(n&1)for(RG int i=0;i<N;i++)f[i]=1ll*f[i]*g[i]%mod;
          for(RG int i=0;i<N;i++)g[i]=1ll*g[i]*g[i]%mod;
          n>>=1;
        }
        FWT_xor(f,N,-1);
        printf("%d
    ",f[0]);
      }
      return 0;
    }
    
    
  • 相关阅读:
    开发工具
    CPU知识
    GMAP.NET
    vtordisp
    Hadoop HBase 配置 安装 Snappy 终极教程
    asp.net Vs访问正常,iis访问出现各种问题的部分处理方法
    MVC项目小结:动态菜单
    视频的采集和动态显示
    《编程之美》
    Nginx实现简单的负载均衡web访问
  • 原文地址:https://www.cnblogs.com/cjfdf/p/9735932.html
Copyright © 2011-2022 走看看