zoukankan      html  css  js  c++  java
  • 3930: [CQOI2015]选数|递推|数论

    题目让求从区间[L,H]中可反复的选出n个数使其gcd=k的方案数
    转化一下也就是从区间[Lk,Hk]中可反复的选出n个数使其gcd=1的方案数
    然后f[i]表示gcd=i的方案数。考虑去掉全部的数都是反复的情况。这样的情况最后在推断一下加上

    f[i]=sumi|jf[j]

    #include<algorithm>
    #include<iostream>
    #include<cstdlib>
    #include<cstring>
    #include<cstdio>
    #include<vector>
    #include<cmath>
    #include<queue>
    #include<set>
    #include<map>
    #define ll long long
    #define mod 1000000007 //2 3 4679 35617
    #define N 100051
    using namespace std;
    int sc()
    {
        int i=0,f=1; char c=getchar();
        while(c>'9'||c<'0'){if(c=='-')f=-1;c=getchar();}
        while(c>='0'&&c<='9')i=i*10+c-'0',c=getchar();
        return i*f;
    }
    long long f[N],n,k,a,b;
    long long cal(ll x,ll y)
    {
        long long res=1;
        for(;y;x=x*x%mod,y>>=1)
            if(y&1)res=res*x%mod;
        return res;
    }
    int main()
    {
        scanf("%d%d%d%d",&n,&k,&a,&b);
        int l=a/k,r=b/k;
        if(a%k)l++;
        for(int i=b-a;i;i--)
        {
            int L=l/i,R=r/i;
            if(l%i)L++;
            if(l<=r)
            {
                f[i]=(cal(R-L+1,n)-(R-L+1))%mod;
                for(int j=i*2;j<=b-a;j+=i)f[i]=(f[i]-f[j])%mod;
            }
        }
        if(l==1)f[1]++;
        printf("%d",(f[1]+mod)%mod);
        return 0;
    }
  • 相关阅读:
    缓存清理
    机器学习在电商领域三大应用,推荐,搜索,广告中商品排序
    并发和并行
    拷贝控制
    gitk
    git GUI Clients
    new delete
    Windows 安装 gcc
    C++ 运算符优先级
    iostream 操作符
  • 原文地址:https://www.cnblogs.com/zhchoutai/p/8310282.html
Copyright © 2011-2022 走看看