AcWing 4658:质因数个数 ← 整数唯一分解定理 + long long

【题目来源】
https://www.acwing.com/problem/content/4661/

【题目描述】
给定正整数 n,请问有多少个质数是 n 的约数。

【输入格式】
输入的第一行包含一个整数 n。

【输出格式】
输出一个整数,表示 n 的质数约数个数。

【输入样例】
396

【输出样例】
3

【数据范围】
对于 30% 的评测用例,1≤n≤10000。
对于 60% 的评测用例,1≤n≤10^9。
对于所有评测用例,1≤n≤10^16。

【算法分析】
● 整数唯一分解定理(算术基本定理)
任何一个大于 1 的正整数 n,都可以唯一地表示成有限个质数的乘积形式:n=p₁ᵏ¹×p₂ᵏ²×...×pₘᵏᵐ,其中 p₁<p₂<...<pₘ 是质数,k₁,k₂,....,kₘ 是正整数.且这种分解方式在不考虑顺序的情况下是唯的。

● 整数唯一分解定理是欧拉函数计算公式的理论基础,欧拉函数是整数唯一分解定理的重要应用之一。通俗地讲,整数唯一分解定理是 "地基",欧拉函数公式是 "盖在地基上的房子";没有地基,房子建不起来;房子的存在,也印证了地基的稳固。

|-------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|-----------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
| 整数唯一分解定理 | 欧拉函数 |
| #include <bits/stdc++.h> using namespace std; typedef long long LL; void cal(LL n) { LL cnt=0; for(LL i=2; i*i<=n; i++) { if(n%i==0) { cnt++; while(n%i==0) n/=i; } } if(n>1) cnt++; cout<<cnt; } int main() { LL x; cin>>x; cal(x); return 0; } /* in:18 out:2 */ | #include <bits/stdc++.h> using namespace std; typedef long long LL; void cal(LL n) { LL cnt=n; for(LL i=2; i*i<=n; i++) { if(n%i==0) { cnt=cnt/i*(i-1); while(n%i==0) n/=i; } } if(n>1) cnt=cnt/n*(n-1); cout<<cnt; } int main() { LL x; cin>>x; cal(x); return 0; } /* in:18 out:6 */ |
| 功能:求 n 的不同质因子的个数。 | 功能:求 1~n 中与 n 互质的正整数的个数。 |

● 欧拉函数
(1)欧拉函数 φ(n) 是数论中的重要函数,用于计算 1~n 中与 n 互质的正整数的个数。特别地,当 n=1 时,φ(1)=1。
(2)欧拉函数的计算公式:若 n 的质因数分解为 n=p₁ᵏ¹×p₂ᵏ²×...×pₘᵏᵐ,则 φ(n)=n×(1-1/p₁)×(1-1/p₂)×...×(1-1/pₘ)。其中,p₁,...,pₘ,是 n 的所有质因数。

● 欧拉函数性质‌
(1)若 p 是质数,φ(p)=p-1。
例如,φ(5)‌=5-1=4(表示 1~5 中与 5 互质的正整数有 1,2,3,4 等 4 个)。
(2)若 n=pᵏ,φ(pᵏ)=pᵏ-pᵏ⁻¹。
例如,φ(8)‌=2³-2²=8-4=4(表示 1~8 中与 8 互质的正整数有 1,3,5,7 等 4 个)
(3)积性函数:当 a,b 互质时,φ(ab)=φ(a)φ(b)。
例如,φ(10)=φ(2)×φ(5)=1×4=4(表示 1~10 中与 10 互质的正整数有 1,3,7,9 等 4 个)
(4)通用计算公式:φ(n)=n×(1-1/p₁)×(1-1/p₂)×...×(1-1/pₘ)。其中,p₁,...,pₘ,是 n 的所有质因数。
例如, 由于 18=2×3²,所以 φ(18)=18×(1-1/2)×(1-1/3)=6(表示 1~18 中与 18 互质的正整数有 1,5,7,11,13,17 等 6 个)。详见:https://blog.csdn.net/hnjzsyjyj/article/details/148135689

【算法代码】

cpp 复制代码
#include <bits/stdc++.h>
using namespace std;

typedef long long LL;

void cal(LL n) {
    LL cnt=0;
    for(LL i=2; i*i<=n; i++) {
        if(n%i==0) {
            cnt++;
            while(n%i==0) n/=i;
        }
    }
    if(n>1) cnt++;
    cout<<cnt;
}

int main() {
    LL x;
    cin>>x;
    cal(x);

    return 0;
}

/*
in:7371287302712134
out:4
*/

【参考文献】
https://blog.csdn.net/hnjzsyjyj/article/details/148176615
https://blog.csdn.net/hnjzsyjyj/article/details/148177392
https://blog.csdn.net/hnjzsyjyj/article/details/158039681
https://blog.csdn.net/hnjzsyjyj/article/details/148159326