AcWing 870.约数个数(算术基本定理)

Issue:

AcWing 870.约数个数(算术基本定理)_第1张图片

Meaning:

  1. 输出所有数乘积的约数个数

Thinking:

  1. 算术基本定理:任何一个大于1的自然数 N,如果 N 不为质数,那么 N 可以唯一分解成有限个质数的乘积 N = P 1 a 1 × P 2 a 2 × P 3 a 3 × ⋯ × P n a n N = P_{1}^{a_1} \times P_{2}^{a_2} \times P_{3}^{a_3} \times \cdots \times P_{n}^{a_n} N=P1a1×P2a2×P3a3××Pnan,这里 P 1 < P 2 < P 3 < ⋯ < P n P_1P1<P2<P3<<Pn 均为质数,其中指数 a i a_i ai 是正整数;
  2. 由题意可知 N N N(所有数的乘积)的约数 d d d 可以表示为 d = P 1 b 1 × P 2 b 2 × P 3 b 3 × ⋯ × P n b n d = P_{1}^{b_1} \times P_{2}^{b_2} \times P_{3}^{b_3} \times \cdots \times P_{n}^{b_n} d=P1b1×P2b2×P3b3××Pnbn,其中的的指数(以 b n b_n bn为例)可以取 [ 0 , a n ] [0, a_n] [0,an],也就是总共可以取到 a n + 1 a_n + 1 an+1个数;
  3. 每一个 b i b_i bi都有 a i + 1 a_i + 1 ai+1 种选择,由乘法原理,约数 d d d 的数量为 ( a 1 + 1 ) × ( a 2 + 1 ) × ( a 3 + 1 ) × ⋯ × ( a n + 1 ) (a_1 + 1) \times (a_2 + 1) \times (a_3 + 1) \times \cdots \times (a_n + 1) (a1+1)×(a2+1)×(a3+1)××(an+1)
  4. 时间复杂度近似 O ( l o g n ) O(log_n) O(logn)

Code:

//约数个数公式:(a1+1)(a2+1)……(ak+1)
//约数之和公式:(p1^0+p1^1+……+p1^a1)(p2^0+p2^1+……+p2^a2)(pk^0+pk^1+……+pk^ak)第二行这里可以先不用看


#include 
#include 
#include    //哈希表 可以键值对的方式 也可以first/second的方式
using namespace std;

const int mod = 1e9+7;  //模

int main()
{
    int n;
    cin >> n;

    unordered_map<int, int>  primes;
    while(n--)
    {
        int x;
        cin >> x;
        for(int i=2; i<=x/i; i++)
            while(x%i==0)
            {
                x /= i;
                primes[i]++;      //存的是pi的值
            }
        if(x > 1)
            primes[x]++;
    }
    long long res = 1;
    for(auto prime : primes)
        res = res * (prime.second+1) % mod;
    cout << res << endl;
    return 0;
} 

Tips:

  1. 记下约数个数公式。

你可能感兴趣的:(enroll)