poj 1845 Sumdiv

来源:互联网 发布:录屏软件fast 编辑:程序博客网 时间:2024/04/27 08:38

知识点:

1

推论5 (除数和函数)

设a是正整数,σ(a)表示a的所有正除数之和,那么σ(1)=1,当a有标准素因数分解式时,

σ(a)=∏((pj^αj+1)-1/(pj – 1))(1<=j<=s)

2

(a + b) % p = (a % p + b % p) % p

(a * b) % p = (a % p * b % p) % p

3

取模运算中不能出现除法,等比数列求和公式不成立。

要用二分递归的方式求等比数列。令sum(p,n)为1+p^1+...+p^n.

n为奇数时,有偶数项,相差n/2+1的为一对,一共有n/2+1对。每一对提出一个1+p^(n/2+1)转化为sum(p,n/2)。

n为偶数时,有奇数项,空出p^n/2这一项,依然是相差n/2+1的为一对,一共有n/2对,每一对提出一个1+p^(n/2+1)。转化为sum( p , n/2-1 ).


附上代码喵:

#include<cstdio>#include<iostream>#include<cstring>using namespace std;const int M=9901;typedef long long ll;ll A,B;ll a[10010];ll factor[10010];ll prime[10010];bool isprime[100010];int cnt=0,num=0;void getprime()//筛质数{memset(isprime,1,sizeof(isprime));memset(prime,0,sizeof(prime));isprime[0]=isprime[1]=0;for(int i=2;i<=100000;i++){if(isprime[i]){prime[cnt++]=i;for(int j=2*i;j<=100000;j+=i){isprime[j]=0;}}}}void getfactor()//分解质因数{num=0;memset(factor,0,sizeof(factor));memset(a,0,sizeof(a));for(int i=0;i<cnt;i++){if(A%prime[i]==0){factor[num]=prime[i];while(A%prime[i]==0)a[num]++,A/=prime[i];num++;}}if(A>1){factor[num]=A;a[num]=1;num++;}}ll quickpow(ll x,ll n)//快速幂{ll ret=1;while(n){if(n&1)ret=ret*x%M;x=x*x%M;n>>=1;}return ret;}ll S(ll p,ll n){if(n==0)return 1;if(n&1){return S(p,n/2)*(1+quickpow(p,n/2+1)%M)%M;}return (S(p,n/2-1)*(1+quickpow(p,n/2+1)%M)%M+quickpow(p,n/2)%M)%M;}void getsum(){long long sum=1;for(int i=0;i<num;i++){sum=sum*S(factor[i],a[i]*B)%M;sum%=M;}printf("%I64d\n",sum);}int main(){getprime();while(scanf("%I64d%I64d",&A,&B)!=EOF){if(A==0){printf("0\n");continue;}getfactor();getsum();}return 0;}





0 0
原创粉丝点击