Counting Divisors
Time Limit: 10000/5000 MS (Java/Others) Memory Limit: 524288/524288 K (Java/Others)Total Submission(s): 3713 Accepted Submission(s): 1366
Problem Description
In mathematics, the function
d(n)
denotes the number of divisors of positive integer
n
.
For example, d(12)=6 because 1,2,3,4,6,12 are all 12 's divisors.
In this problem, given l,r and k , your task is to calculate the following thing :
For example, d(12)=6 because 1,2,3,4,6,12 are all 12 's divisors.
In this problem, given l,r and k , your task is to calculate the following thing :
(∑i=lrd(ik))mod998244353
Input
The first line of the input contains an integer
T(1≤T≤15)
, denoting the number of test cases.
In each test case, there are 3 integers l,r,k(1≤l≤r≤1012,r−l≤106,1≤k≤107) .
In each test case, there are 3 integers l,r,k(1≤l≤r≤1012,r−l≤106,1≤k≤107) .
Output
For each test case, print a single line containing an integer, denoting the answer.
Sample Input
3 1 5 1 1 10 2 1 100 3
Sample Output
10 48 2302
题意: 给出 l, r, k.求:(lambda d(i^k))mod998244353,其中 l <= i <= r, d(i) 为 i 的因子个数.
思路:若 x 分解成质因子乘积的形式为 x = p1^a1 * p2^a2 * ... * pn^an,那么 d(x) = (a1 + 1) * (a2 + 1) * ... * (an + 1) .显然 d(x^k) = (a1 * k + 1) * (a2 * k + 1) * ... * (an * k + 1) .
#include<iostream>
#include<stdio.h>
#include<string.h>
using namespace std;
typedef long long ll;
const int maxn=1000100;
const ll mod=998244353;
ll prime[maxn]; //第i个素数
bool is_prime[maxn]; //is_prime[i]为true表示i是素数
ll sum[maxn]; //代表每个数的k次的因子个数
ll a[maxn];
//返回n以内的素数的个数
int sieve(int n)
{
int p = 0;
memset(is_prime,true,sizeof(is_prime));
is_prime[0] = is_prime[1] = false;
for (int i = 2; i <= n; i++){
if (is_prime[i]){
prime[p++] = i;
for (int j = 2 * i; j <= n; j += i)
is_prime[j] = false;
}
}
return p;
}
int main()
{
int p1=sieve(maxn-1);
int t;
ll l,r,k;
scanf("%d",&t);
while(t--)
{
scanf("%lld%lld%lld",&l,&r,&k);
for(int i=0;i<=r-l;i++)
{
sum[i]=1;
a[i]=i+l;
}
for(int i=0;prime[i]*prime[i]<=r;i++)
{
ll x=(l/prime[i]+(l%prime[i]?1:0))*prime[i];
for(ll p=x;p<=r;p+=prime[i])
{
ll tmp=0;
while(a[p-l]%prime[i]==0)
{
tmp++;
a[p-l]/=prime[i];
}
sum[p-l]=(sum[p-l]*(tmp*k+1)%mod)%mod;
}
}
ll ans=0;
for(int i=0;i<=r-l;i++)
{
//其含有的质因子中有大于1e6的质数,需要加入计算
if(a[i]!=1)sum[i]=(sum[i]*(k+1))%mod;
ans=(ans+sum[i])%mod;
}
printf("%lld\n",ans);
}
}