• BZOJ 2627 JZPKIL


    题面:

    2627: JZPKIL

    Time Limit: 50 Sec  Memory Limit: 128 MB
    Submit: 347  Solved: 104
    [Submit][Status][Discuss]

    Description

    Input

    第一行,询问个数T。
      下面T行,每行三个整数,n, x, y。

    Output

      T行,每行一个整数,表示相应的询问的答案

    Sample Input

    5
    6 0 0
    6 0 1
    6 1 0
    6 1 1
    1000000000 50 50

    Sample Output

    6
    66
    15
    126
    393442025

    HINT

    数据规模和约定
    30%的数据,x=y
    另30%的数据,n<=10^9, x, y<=100
    100%的数据,T<=100, 1<=n<=10^18, 0<=x, y<=3000

    这题是个50sec卡评测反演好题。

    $quad sum_{i=1}^{n}(i,n)^{x}[i,n]^{y}$

    $=sum_{i=1}^{n}(i,n)^{x-y}(icdot n)^{y}$

    $=n^{y}sum_{i=1}^{n}(i,n)^{x-y}i^{y}$

    $=n^{y}sum_{d|n}d^{x}sum_{i=1}^{frac{n}{d}}sum_{k|i,k|frac{n}{d}}mu(k)i^{y}$

    $=n^{y}sum_{d|n}d^{x}sum_{k|frac{n}{d}}mu(k)k^{y}sum_{i=1}^{frac{n}{kcdot d}i^{y}}$

    $=n^{y}sum_{d|n}d^{x}sum_{k|frac{n}{d}}mu(k)k^{y}sum_{i=0}^{y}frac{1}{y+1}dbinom{y+1}{i}B_{i}(frac{n}{kcdot d})^{y+1-i}$

    $=sum_{i=0}^{y}t_{i}n^{y}sum_{d|n}d^{x}sum_{k|frac{n}{d}}mu(k)k^{y}(frac{n}{kcdot d})^{y+1-i}$

    $t_{i}=frac{1}{y+1}dbinom{y+1}{i}B_{i}$ ($B_{i}$为伯努利数)

    将$n$分解质因数$n=p_{1}^{k_1}cdot p_{2}^{k_2}cdot p_{3}^{k_3}cdots $

    令$f(p_{j}^{k_j},i)=sum_{d|p_{j}^{k_j}}d^{p_{j}^{k_j}}sum_{k|frac{p_{j}^{k_j}}{d}}mu(k)k^{y}(frac{p_{j}^{k_j}}{kcdot d})^{y+1-i}$

    $f$为积性函数,可以用每个质因子的答案相乘得到$n$的答案。

    但是由于$n$很大,我们只能用$Pollard_rho$分解大数因子。

    时间复杂度为$O(y^{2}+Tcdot n^{frac{1}{4}}+Tcdot ycdot log;n)$

      1 #include <iostream>
      2 #include <stdio.h>
      3 #include <algorithm>
      4 using namespace std;
      5 #define LL long long
      6 template<typename __>
      7 inline void read(__ &s)
      8 {
      9     char ch=getchar();
     10     for(s=0;ch<'0'||ch>'9';ch=getchar());
     11     for(;ch>='0'&&ch<='9';s=s*10+ch-'0',ch=getchar());
     12 }
     13 namespace Pollard_rho
     14 {
     15     inline LL mul(LL x,LL y,LL mod)
     16     {
     17         return (x*y-(LL)(x/(long double)mod*y+0.5)*mod+mod)%mod;
     18     }
     19     inline LL qpow(LL x,LL y,LL mod)
     20     {
     21         LL ans=1;
     22         for(;y;y>>=1,x=mul(x,x,mod))
     23             if(y&1)
     24                 ans=mul(ans,x,mod);
     25         return ans;
     26     }
     27     inline bool judge(LL n,LL p)
     28     {
     29         if(n<=p)
     30             return 1;
     31         if(n%p==0)
     32             return 0;
     33         LL x=n-1;
     34         int s=-1;
     35         while(!(x&1))
     36             x>>=1,++s;
     37         x=qpow(p,x,n);
     38         if(x==1||x==n-1)
     39             return 1;
     40         while(s--)
     41         {
     42             x=mul(x,x,n);
     43             if(x==1)
     44                 return 0;
     45             if(x==n-1)
     46                 return 1;
     47         }
     48         return 0;
     49     }
     50     inline bool miller_rabin(LL n)
     51     {
     52         return judge(n,2)&&judge(n,3)&&judge(n,5)&&judge(n,7)&&judge(n,11)&&judge(n,13)&&judge(n,17)&&judge(n,19)&&judge(n,23);
     53     }
     54     LL *P;
     55     int Pcnt;
     56     inline LL pollard_rho(LL n)
     57     {
     58         LL x=rand()%(n-1)+1,xx=mul(x,x,n)+1,t=1;
     59         while(t==1)
     60         {
     61             x=mul(x,x,n)+1;
     62             xx=mul(xx,xx,n)+1;
     63             xx=mul(xx,xx,n)+1;
     64             t=__gcd(x-xx+n,n);
     65         }
     66         return t;
     67     }
     68     inline void divide(LL n)
     69     {
     70         if(n==1)
     71             return ;
     72         else
     73             if(n%2==0)
     74                 P[++Pcnt]=2,divide(n/2);
     75             else
     76                 if(miller_rabin(n))
     77                     P[++Pcnt]=n;
     78                 else
     79                 {
     80                     LL x=pollard_rho(n);
     81                     divide(x);
     82                     divide(n/x);
     83                 }
     84     }
     85     inline void init(LL n,LL *p,int &cnt)
     86     {
     87         P=p;
     88         Pcnt=0;
     89         divide(n);
     90         cnt=Pcnt;
     91     }
     92 }
     93 #define mod 1000000007
     94 inline int mul(int x,int y)
     95 {
     96     return ((LL)x*y)%mod;
     97 }
     98 inline int add(int x,int y)
     99 {
    100     x+=y;
    101     if(x>=mod)
    102         x-=mod;
    103     return x;
    104 }
    105 inline int dec(int x,int y)
    106 {
    107     x-=y;
    108     if(x<0)
    109         x+=mod;
    110     return x;
    111 }
    112 inline int qpow(int x,int y)
    113 {
    114     x%=mod;
    115     int ans=1;
    116     for(;y;y>>=1,x=mul(x,x))
    117         if(y&1)
    118             ans=mul(ans,x);
    119     return ans;
    120 }
    121 #define maxn 3002
    122 int B[maxn],C[maxn][maxn],a[maxn],pw[20][maxn],iv[20][maxn];
    123 int p[20],c[20],x,y,N;
    124 LL n;
    125 int tot;
    126 inline void init()
    127 {
    128     int i,j;
    129     C[0][0]=1;
    130     for(i=1;i<=3001;i++)
    131     {
    132         C[i][0]=1;
    133         for(j=1;j<=i;j++)
    134             C[i][j]=add(C[i-1][j],C[i-1][j-1]);  
    135     }
    136     B[0]=1;
    137     for(i=1;i<=3001;i++)
    138     {
    139         for(j=0;j<i;++j)
    140             B[i]=dec(B[i],mul(C[i+1][j],B[j]));
    141         B[i]=mul(B[i],qpow(i+1,mod-2));
    142     }
    143 }
    144 inline void pre()
    145 {
    146     for(int i=0;i<=y+1;i++)
    147         a[i]=0;
    148     for(int i=0;i<=y;i++)
    149         a[y+1-i]=mul(C[y+1][i],B[i]);
    150     int tmp=qpow(y+1,mod-2);
    151     for(int i=0;i<=y+1;i++)
    152         a[i]=mul(a[i],tmp);
    153     a[y]=add(a[y],1);
    154     if(!y)
    155         a[0]=dec(a[0],1);
    156 }
    157 inline void get_frac()
    158 {
    159     static LL frac[97];
    160     int cnt=0;
    161     tot=0;
    162     Pollard_rho::init(n,frac,cnt);
    163     sort(frac+1,frac+cnt+1);
    164     for(int i=1;i<=cnt;i++)
    165         if(frac[i]!=frac[i-1])
    166             p[++tot]=frac[i]%mod,c[tot]=1;
    167         else
    168             ++c[tot];
    169     for(int i=1;i<=tot;i++)
    170     {
    171         pw[i][0]=iv[i][0]=1;
    172         int t=max(max(x,y),c[i])+1;
    173         for(int j=1;j<=t;j++)
    174             pw[i][j]=mul(pw[i][j-1],p[i]);
    175         int v=qpow(p[i],mod-2);
    176         for(int j=1;j<=t;j++)
    177             iv[i][j]=mul(iv[i][j-1],v);
    178     }
    179 }
    180 inline int geo(int i,int x)
    181 {
    182     int c=::c[i];
    183     int p;
    184     if(x<0)
    185         p=iv[i][-x];
    186     else
    187         p=pw[i][x];
    188     if(p==1)
    189         return c;
    190     int ans=0,t=p;
    191     for(int j=1;j<=c;j++)
    192     {
    193         ans=add(ans,t);
    194         t=mul(t,p);
    195     }
    196     return ans;
    197 }
    198 inline void input()
    199 {
    200     read(n);
    201     read(x);
    202     read(y);
    203     unsigned int rand_seed=18230742;
    204     rand_seed+=(n+(x<<16)+y)+(rand_seed<<2);
    205     srand(rand_seed);
    206 }
    207 inline int calc(int x,int y)
    208 {
    209     int ans=x<0?qpow(qpow(N,mod-2),-x):qpow(N,x);
    210     for(int i=1;i<=tot;i++)
    211     {
    212         int t1=geo(i,-x);
    213         int t2=dec(1,y>=0?pw[i][y]:qpow(p[i],mod-2));
    214         ans=mul(ans,add(1,mul(t1,t2)));
    215     }
    216     return ans;
    217 }
    218 void solve()
    219 {
    220     pre();
    221     get_frac();
    222     N=n%mod;
    223     if(!N)
    224         return (void)(puts("0"));
    225     int ans=0;
    226     int t=1,tmp;
    227     for(int i=0;i<=y+1;i++)
    228     {
    229         tmp=calc(x-i,y-i);
    230         ans=add(ans,mul(mul(a[i],t),tmp));
    231         t=mul(t,N);
    232     }
    233     ans=mul(ans,qpow(N,y));
    234     printf("%d
    ",ans);
    235 }
    236 int main()
    237 {
    238     init();
    239     int T;
    240     read(T);
    241     while(T--)
    242     {
    243         input();
    244         solve();
    245     }
    246 }
    BZOJ 2627

    PS:$Pollard_rho$写丑了会TLE,需要大力卡一波常数才能过。

  • 相关阅读:
    数据库调优2
    数据库调优
    SQL优化
    支付宝/阿里面试题
    Servlet 工程 web.xml 中的 servlet 和 servlet-mapping 标签 《转载》
    《转载》struts旅程《2》
    《转载》struts旅程《1》
    jsp 自定义标签
    body-content取值的意义
    jsp页面中jstl标签详解
  • 原文地址:https://www.cnblogs.com/radioteletscope/p/7675375.html
Copyright © 2020-2023  润新知