Number of divisors of product of N numbers

Given an array arr[] of integers, the task is to count the number of divisors of product of all the elements from given array.

Examples:

Input: arr[] = {3, 5, 7}
Output: 8
3 * 5 * 7 = 105.
Factors of 105 are 1, 3, 5, 7, 15, 21, 35 and 105.

Input: arr[] = {5, 5}
Output: 3
5 * 5 = 25.
Factors of 25 are 1, 5 and 25.

Recommended: Please try your approach on {IDE} first, before moving on to the solution.

A simple solution is to multiply all the N integers and count the number of divisors of the product. However, if the product goes above 107 then we can’t use this approach because numbers greater than 10^7 can’t be prime factorized efficiently using the sieve approach.
An efficient solution does not involve the calculation of the product of all the numbers. We already know that when we multiply 2 numbers, powers get added. For example,

A = 27, B = 23
A * B = 210
Therefore, we need to maintain the count of every power in the product of numbers which can be done by adding counts of powers from every element.

Hence, to compute the number of divisors, the main focus is on the count of primes encountered. So we will stress only on the primes encountered in the product without bothering about the product itself. While traversing through the array, we keep the count of every prime encountered.

Number of divisors = (p1 + 1) * (p2 + 1) * (p3 + 1) * … * (pn + 1)
where p1, p2, p3, …, pn are the primes encountered in the prime factorization of all the elements.

Below is the implementation of the above approach:

C++

 // C++ implementation of the approach #include #define MAX 10000002    using namespace std; int prime[MAX];    // Array to store count of primes int prime_count[MAX];    // Function to store smallest prime factor // of every number till MAX void sieve() {     memset(prime, 0, sizeof(prime));     prime = prime = 1;     for (int i = 2; i * i < MAX; i++) {         if (prime[i] == 0) {             for (int j = i * 2; j < MAX; j += i) {                 if (prime[j] == 0)                     prime[j] = i;             }         }     }     for (int i = 2; i < MAX; i++) {            // If the number is prime then it's          // smallest prime factor is the number          // itself         if (prime[i] == 0)             prime[i] = i;     } }    // Function to return the count of the divisors for // the product of all the numbers from the array long long numberOfDivisorsOfProduct(const int* arr,                                             int n) {     memset(prime_count, 0, sizeof(prime_count));        for (int i = 0; i < n; i++) {         int temp = arr[i];         while (temp != 1) {                // Increase the count of prime             // encountered             prime_count[prime[temp]]++;             temp = temp / prime[temp];         }     }        long long ans = 1;        // Multiplying the count of primes     // encountered     for (int i = 2; i < MAX; i++) {         ans = ans * (prime_count[i] + 1);     }        return ans; }    // Driver code int main() {     sieve();     int arr[] = { 2, 4, 6 };     int n = sizeof(arr) / sizeof(arr);     cout << numberOfDivisorsOfProduct(arr, n);     return 0; }

Java

 // Java implementation of the approach    import java.util.Arrays;    // Java implementation of the approach class GFG {        final static int MAX = 10000002;        static int prime[] = new int[MAX];    // Array to store count of primes     static int prime_count[] = new int[MAX];    // Function to store smallest prime factor // of every number till MAX     static void sieve() {         Arrays.fill(prime, 0, MAX, 0);         prime = prime = 1;         for (int i = 2; i * i < MAX; i++) {             if (prime[i] == 0) {                 for (int j = i * 2; j < MAX; j += i) {                     if (prime[j] == 0) {                         prime[j] = i;                     }                 }             }         }         for (int i = 2; i < MAX; i++) {                // If the number is prime then it's              // smallest prime factor is the number              // itself             if (prime[i] == 0) {                 prime[i] = i;             }         }     }    // Function to return the count of the divisors for // the product of all the numbers from the array     static long numberOfDivisorsOfProduct(int[] arr,             int n) {         Arrays.fill(prime_count, 0, MAX, 0);            for (int i = 0; i < n; i++) {             int temp = arr[i];             while (temp != 1) {                    // Increase the count of prime                 // encountered                 prime_count[prime[temp]]++;                 temp = temp / prime[temp];             }         }            long ans = 1;            // Multiplying the count of primes         // encountered         for (int i = 2; i < MAX; i++) {             ans = ans * (prime_count[i] + 1);         }            return ans;     }    // Driver code     public static void main(String[] args) {         sieve();         int arr[] = {2, 4, 6};         int n = arr.length;         System.out.println(numberOfDivisorsOfProduct(arr, n));        } }     // This code is contributed by 29AjayKumar

Python3

 # Python3 implementation of the approach  MAX = 10000002 prime =  * (MAX)  MAX_sqrt = int(MAX ** (0.5))    # Array to store count of primes  prime_count =  * (MAX)    # Function to store smallest prime # factor in prime[]  def sieve():         prime, prime = 1, 1     for i in range(2, MAX_sqrt):          if prime[i] == 0:              for j in range(i * 2, MAX, i):                  if prime[j] == 0:                      prime[j] = i             for i in range(2, MAX):             # If the number is prime then it's          # the smallest prime factor is the         # number itself          if prime[i] == 0:             prime[i] = i     # Function to return the count of the divisors for  # the product of all the numbers from the array  def numberOfDivisorsOfProduct(arr, n):         for i in range(0, n):         temp = arr[i]          while temp != 1:                 # Increase the count of prime              # encountered              prime_count[prime[temp]] += 1             temp = temp // prime[temp]         ans = 1        # Multiplying the count of primes      # encountered      for i in range(2, len(prime_count)):         ans = ans * (prime_count[i] + 1)             return ans     # Driver code  if __name__ == "__main__":         sieve()      arr = [2, 4, 6]      n = len(arr)     print(numberOfDivisorsOfProduct(arr, n))     # This code is contributed by Rituraj Jain

C#

 // C# implementation of the approach using System; public class GFG {         static int MAX = 1000000;         static int []prime = new int[MAX];     // Array to store count of primes      static int []prime_count = new int[MAX];     // Function to store smallest prime factor  // of every number till MAX      static void sieve() {           for(int i =0;i

Output:

10

In a memory efficient approach, the array can be replaced by an unordered map to store count of only those primes which have been encountered.

Below is the implementation of the memory efficient approach:

C++

 // C++ implementation of the approach #include #define MAX 10000002    using namespace std; int prime[MAX];    // Map to store count of primes unordered_map prime_count;    // Function to store smallest prime factor  // in prime[] void sieve() {     memset(prime, 0, sizeof(prime));     prime = prime = 1;     for (int i = 2; i * i < MAX; i++) {         if (prime[i] == 0) {             for (int j = i * 2; j < MAX; j += i) {                 if (prime[j] == 0)                     prime[j] = i;             }         }     }     for (int i = 2; i < MAX; i++) {            // If the number is prime then         // it's the smallest prime factor          // is the number itself         if (prime[i] == 0)             prime[i] = i;     } }    // Function to return the count of the divisors for // the product of all the numbers from the array long long numberOfDivisorsOfProduct(const int* arr,                                              int n) {        for (int i = 0; i < n; i++) {         int temp = arr[i];         while (temp != 1) {                // Increase the count of prime             // encountered             prime_count[prime[temp]]++;             temp = temp / prime[temp];         }     }        long long ans = 1;        // Multiplying the count of primes      // encountered     unordered_map::iterator it;     for (it = prime_count.begin();          it != prime_count.end(); it++) {         ans = ans * (it->second + 1);     }        return ans; }    // Driver code int main() {     sieve();     int arr[] = { 3, 5, 7 };     int n = sizeof(arr) / sizeof(arr);     cout << numberOfDivisorsOfProduct(arr, n);     return 0; }

Python3

 # Python3 implementation of the approach  from collections import defaultdict    MAX = 10000002 prime =  * (MAX)  MAX_sqrt = int(MAX ** (0.5))    # Map to store count of primes  prime_count = defaultdict(lambda:0)    # Function to store smallest prime  # factor in prime[]  def sieve():         prime, prime = 1, 1     for i in range(2, MAX_sqrt):          if prime[i] == 0:              for j in range(i * 2, MAX, i):                  if prime[j] == 0:                      prime[j] = i             for i in range(2, MAX):             # If the number is prime then          # it's the smallest prime factor          # is the number itself          if prime[i] == 0:             prime[i] = i     # Function to return the count of the divisors for  # the product of all the numbers from the array  def numberOfDivisorsOfProduct(arr, n):         for i in range(0, n):         temp = arr[i]          while temp != 1:                 # Increase the count of prime              # encountered              prime_count[prime[temp]] += 1             temp = temp // prime[temp]         ans = 1        # Multiplying the count of primes      # encountered      for key in prime_count:         ans = ans * (prime_count[key] + 1)             return ans     # Driver code  if __name__ == "__main__":         sieve()      arr = [3, 5, 7]      n = len(arr)     print(numberOfDivisorsOfProduct(arr, n))     # This code is contributed by Rituraj Jain

Output:

8

My Personal Notes arrow_drop_up An enthusiastic Java and web developer with a little affinity for tea, cricket, English, etymology, and reading

If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please Improve this article if you find anything incorrect by clicking on the "Improve Article" button below.