zoukankan      html  css  js  c++  java
  • BZOJ 3209: 花神的数论题 [数位DP]

    3209: 花神的数论题

    题意:求(1到nle 10^{15})二进制1的个数的乘积,取模1e7+7


    二进制最多50位,我们统计每种1的个数的数的个数,快速幂再乘起来就行了
    裸数位DP..(f[i][j])i位数j个1的方案数..不考虑天际线就是组合数...


    比较坑的地方是本题求f要取模(phi(1e7+7)),然后它并不是质数...

    #include <iostream>
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    #include <cmath>
    using namespace std;
    typedef long long ll;
    const int N=60;
    const ll P=10000007, Phi=9988440;
    inline ll read(){
    	char c=getchar();ll x=0,f=1;
    	while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
    	while(c>='0'&&c<='9'){x=x*10+c-'0';c=getchar();}
    	return x*f;
    }
    
    ll n, ans=1; int a[N], len;
    ll Pow(ll a, ll b) { //printf("Pow %lld %lld
    ",a,b);
    	ll ans=1;
    	for(; b; b>>=1, a=a*a%P) 
    		if(b&1) ans=ans*a%P;
    	return ans;
    }
    ll f[N][N];
    ll dfs(int d, int sky, int x) {
    	if(d==0) return x==0;
    	if(!sky) return f[d][x];
    	int lim = sky ? a[d] : 1; 
    	ll now=0;
    	for(int i=0; i<=lim; i++) (now += dfs(d-1, sky && i==lim, x-i))%=Phi;
    	return sky ? now : f[d][x]=now;
    }
    int main() {
    	freopen("in","r",stdin);
    	n=read(); 
    	while(n) a[++len]=n&1, n>>=1;
    	//memset(f,-1,sizeof(f));
    	f[0][0]=1;
    	for(int i=1; i<=len; i++){
    		f[i][0]=1;
    		for(int j=1; j<=i; j++) f[i][j]=(f[i-1][j]+f[i-1][j-1])%Phi;
    	}
    	for(int i=2; i<=len; i++)
    		ans = ans*Pow(i, dfs(len, 1, i) )%P;
    	printf("%lld", ans);
    }
    
  • 相关阅读:
    设计模式之里氏替换原则
    设计模式之依赖倒转原则
    设计模式之接口分离原则
    spring 集成 kafka producer(KafkaTemplate)
    jmeter 分布式
    ant+Jenkins+jmeter
    pycharm+git+github项目上传
    Python_pip下载不下来源解决方案
    linux_python3环境搭建
    Jenkins+Git+Github+Python自动化化接口项目例子
  • 原文地址:https://www.cnblogs.com/candy99/p/6629005.html
Copyright © 2011-2022 走看看