SPOJ NUMTRYE - Number Theory (Easy)【數論】

題目鏈接:https://www.spoj.com/problems/NUMTRYE/
題目大意:任意一個整數nn都可以寫成n=p1a1p2a2pkak,pin=p_1^{a_1}*p_2^{a_2}*\cdots*p_k^{a_k},p_i均爲素數。定義了兩個函數:f(n)=(pi2ei+1+1)f(n)=\prod ({p_i^{2e_i+1}+1})pip_inn的素因子且eie_ipip_i的最高次。

g(n)=i=1ng(n)=\sum_{i=1}^n(ngcd(n,i))\frac {n}{gcd(n,i)})

給定nn,求:f(n)g(n)\frac {f(n)}{g(n)}%1000000007。

思路:有個定理:

n=p1a1p2a2pkak,pin=p_1^{a_1}*p_2^{a_2}*\cdots*p_k^{a_k},p_i均爲素數。

g(n)=i=1ng(n)=\sum_{i=1}^n(ngcd(n,i))=(p12a1+1+1p1+1)(p22a2+1+1p2+1)(pk2ak+1+1pk+1)\frac {n}{gcd(n,i)})=(\frac {p_1^{2a_1+1}+1}{p_1+1})*(\frac {p_2^{2a_2+1}+1}{p_2+1})*\cdots*(\frac {p_k^{2a_k+1}+1}{p_k+1})

那麼:f(n)g(n)\frac {f(n)}{g(n)}%1000000007=(p1+1)(p2+1)(pk+1)(p_1+1)*(p_2+1)*\cdots*(p_k+1)%1000000007

AC代碼:

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll mod=1000000007;
ll n;
const int maxn=1e6+10;
ll prime[maxn];
int vis[maxn];
int tot=0;
void pre()
{
    for(ll i=2;i<maxn;i++){
        if(vis[i]==0){
            prime[tot++]=i;
            for(ll j=i*2;j<maxn;j+=i){
                vis[j]=1;
            }
        }
    }
}
int main()
{
    int t;
    scanf("%d",&t);
    pre();
    while(t--){
        scanf("%lld",&n);
        ll ans=1;
        for(int i=0;prime[i]*prime[i]<=n;i++){
            if(n%prime[i]==0){
                ans=ans*(prime[i]+1)%mod;
            }
            while(n%prime[i]==0){
                n/=prime[i];
            }
        }
        if(n>1){
            ans=ans*(n+1)%mod;
        }
        printf("%lld\n",ans);
    }
    return 0;
}

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章