Maximum Length of Sequence of Sums of prime factors generated by the given operations

Given two integers N and M, the task is to perform the following operations:

  • For every value in the range [N, M], calculate the sum of its prime factors followed by the sum of prime factors of that sum and so on.
  • Generate the above sequence for each array element and calculate the length of the sequence.

    Illustration 
    N = 8 
    Prime factors = {2, 2, 2}. Sum = 2 + 2 + 2 = 6. 
    Prime factors of 6 = {2, 3}. Sum = 2 + 3 = 5. 
    Now 5 cannot be reduced further. 
    Therefore, the sequence is {8, 6, 5}. The length of the sequence is 3.

  • Find the maximum length of such subsequence generated.

Examples:

Input: N = 5, M = 10 
Output: 3 
Explanation: 
For N = 5, the sequence is {5}, so length is 1 
For N = 6, the sequence is {6, 5}, so length is 2 
For N = 7, the sequence is {7}, so length is 1 
For N = 8, the sequence is {8, 6, 5}, so length is 3 
For N = 9, the sequence is {9, 6, 5}, so length is 3 
For N = 10, the sequence is {10, 7}, so length is 2 
Therefore, maximum length of sequence in this range is 3.

Input: N = 2, M = 14 
Output: 4

Naive Approach: The simplest approach to solve the problem is to iterate over the range [N, M], and for each integer, find its prime factors and sum them and repeat this for the sum obtained as well recursively until a sum which itself is a prime is obtained.

Efficient Approach: The above approach can be optimized using Dynamic Programming. Follow the steps below to solve the problem:



  • Precompute the prime numbers using the Sieve of Eratosthenes method.
  • Precompute the smallest prime factors of every integer to find out the prime factors, using Prime Factorization using Sieve.
  • Now, for every integer in the range [N, M], calculate the sum of prime factors and repeat recursively for the obtained sum. Store the length of the sequecne in the dp[] array, to avoid recomputation. If the sum obtained is a prime number, store further computation.
  • Update the maximum length obtained and repeat the above step for every number in the range [N, M], except 4, which leads to infinite loop.
  • Print the maixmum length obtained.

Below is the implementation of the above approach:

C++

filter_none

edit
close

play_arrow

link
brightness_4
code

// C++ Program to implement
// the above approach
#include <bits/stdc++.h>
using namespace std;
  
// Smallest prime factor array
int spf[100005];
  
// Stores if a number is prime or not
bool prime[100005];
  
int dp[100005];
  
// Function to compute all primes
// using Sieve of Eratosthenes
void sieve()
{
    prime[0] = prime[1] = false;
  
    for (int i = 2; i < 100005; i++)
        prime[i] = true;
  
    for (int i = 2; i * i < 100005; i++) {
        if (prime[i]) {
            for (int j = i * i; j < 100005; j += i) {
                prime[j] = false;
            }
        }
    }
}
  
// Function for finding smallest
// prime factors for every integer
void smallestPrimeFactors()
{
    for (int i = 0; i < 100005; i++)
        spf[i] = -1;
    for (int i = 2; i * i < 100005; i++) {
        for (int j = i; j < 100005; j += i) {
            if (spf[j] == -1) {
                spf[j] = i;
            }
        }
    }
}
  
// Function to find the sum of
// prime factors of number
int sumOfPrimeFactors(int n)
{
  
    int ans = 0;
    while (n > 1) {
  
        // Add smallest prime
        // factor to the sum
        ans += spf[n];
  
        // Reduce N
        n /= spf[n];
    }
  
    // Return the answer
    return ans;
}
  
// Function to return the length of
// sequence of for the given number
int findLength(int n)
{
  
    // If the number is prime
    if (prime[n]) {
        return 1;
    }
  
    // If a previously computed
    // subproblem occurred
    if (dp[n]) {
        return dp[n];
    }
  
    // Calculate the sum of
    // prime factors
    int sum = sumOfPrimeFactors(n);
  
    return dp[n] = 1 + findLength(sum);
}
  
// Function to return the maximum length
// of sequence for the given range
int maxLength(int n, int m)
{
  
    // Pre-calculate primes
    sieve();
  
    // Precalculate smllest
    // prime factors
    smallestPrimeFactors();
  
    int ans = INT_MIN;
  
    // Iterate over the range
    for (int i = n; i <= m; i++) {
        if (i == 4) {
            continue;
        }
  
        // Update maximum length
        ans = max(ans, findLength(i));
    }
  
    return ans;
}
  
// Driver Code
int main()
{
    int n = 2, m = 14;
  
    cout << maxLength(n, m);
}

chevron_right


Java

filter_none

edit
close

play_arrow

link
brightness_4
code

// Java Program to implement
// the above approach
import java.util.*;
class GFG{
  
// Smallest prime factor array
static int spf[] = new int[100005];
  
// Stores if a number is prime or not
static boolean prime[] = new boolean[100005];
  
static int dp[] = new int[100005];
  
// Function to compute all primes
// using Sieve of Eratosthenes
static void sieve()
{
    prime[0] = prime[1] = false;
  
    for (int i = 2; i < 100005; i++)
        prime[i] = true;
  
    for (int i = 2; i * i < 100005; i++) 
    {
        if (prime[i])
        {
            for (int j = i * i; j < 100005; j += i) 
            {
                prime[j] = false;
            }
        }
    }
}
  
// Function for finding smallest
// prime factors for every integer
static void smallestPrimeFactors()
{
    for (int i = 0; i < 100005; i++)
        spf[i] = -1;
    for (int i = 2; i * i < 100005; i++) 
    {
        for (int j = i; j < 100005; j += i)
        {
            if (spf[j] == -1
            {
                spf[j] = i;
            }
        }
    }
}
  
// Function to find the sum of
// prime factors of number
static int sumOfPrimeFactors(int n)
{
  
    int ans = 0;
    while (n > 1)
    {
  
        // Add smallest prime
        // factor to the sum
        ans += spf[n];
  
        // Reduce N
        n /= spf[n];
    }
  
    // Return the answer
    return ans;
}
  
// Function to return the length of
// sequence of for the given number
static int findLength(int n)
{
  
    // If the number is prime
    if (prime[n]) 
    {
        return 1;
    }
  
    // If a previously computed
    // subproblem occurred
    if (dp[n] != 0
    {
        return dp[n];
    }
  
    // Calculate the sum of
    // prime factors
    int sum = sumOfPrimeFactors(n);
  
    return dp[n] = 1 + findLength(sum);
}
  
// Function to return the maximum length
// of sequence for the given range
static int maxLength(int n, int m)
{
  
    // Pre-calculate primes
    sieve();
  
    // Precalculate smllest
    // prime factors
    smallestPrimeFactors();
  
    int ans = Integer.MIN_VALUE;
  
    // Iterate over the range
    for (int i = n; i <= m; i++)
    {
        if (i == 4)
        {
            continue;
        }
  
        // Update maximum length
        ans = Math.max(ans, findLength(i));
    }
  
    return ans;
}
  
// Driver Code
public static void main(String[] args)
{
    int n = 2, m = 14;
  
    System.out.print(maxLength(n, m));
}
}
  
// This code is contributed by Princi Singh

chevron_right


Python3

filter_none

edit
close

play_arrow

link
brightness_4
code

# Python3 program to implement
# the above approach
import sys
  
# Smallest prime factor array
spf = [0] * 100005
  
# Stores if a number is prime or not
prime = [False] * 100005
  
dp = [0] * 100005
  
# Function to compute all primes
# using Sieve of Eratosthenes
def sieve():
  
    for i in range(2, 100005):
        prime[i] = True
          
    i = 2
    while i * i < 100005:
        if(prime[i]):
            for j in range(i * i, 100005, i):
                prime[j] = False
                  
        i += 1
  
# Function for finding smallest
# prime factors for every integer
def smallestPrimeFactors():
  
    for i in range(10005):
        spf[i] = -1
  
    i = 2
    while i * i < 100005:
        for j in range(i, 100005, i):
            if(spf[j] == -1):
                spf[j] = i
  
        i += 1
  
# Function to find the sum of
# prime factors of number
def sumOfPrimeFactors(n):
  
    ans = 0
    while(n > 1):
  
        # Add smallest prime
        # factor to the sum
        ans += spf[n]
  
        # Reduce N
        n //= spf[n]
  
    # Return the answer
    return ans
  
# Function to return the length of
# sequence of for the given number
def findLength(n):
  
    # If the number is prime
    if(prime[n]):
        return 1
  
    # If a previously computed
    # subproblem occurred
    if(dp[n]):
        return dp[n]
  
    # Calculate the sum of
    # prime factors
    sum = sumOfPrimeFactors(n)
  
    dp[n] = 1 + findLength(sum)
  
    return dp[n]
  
# Function to return the maximum length
# of sequence for the given range
def maxLength(n, m):
  
    # Pre-calculate primes
    sieve()
  
    # Precalculate smllest
    # prime factors
    smallestPrimeFactors()
  
    ans = -sys.maxsize - 1
  
    # Iterate over the range
    for i in range(n, m + 1):
        if(i == 4):
            continue
  
        # Update maximum length
        ans = max(ans, findLength(i))
  
    return ans
  
# Driver Code
n = 2
m = 14
  
# Function call
print(maxLength(n, m))
  
# This code is contributed by Shivam Singh

chevron_right


C#

filter_none

edit
close

play_arrow

link
brightness_4
code

// C# program to implement
// the above approach
using System;
  
class GFG{
  
// Smallest prime factor array
static int []spf = new int[100005];
  
// Stores if a number is prime or not
static bool []prime = new bool[100005];
  
static int []dp = new int[100005];
  
// Function to compute all primes
// using Sieve of Eratosthenes
static void sieve()
{
    prime[0] = prime[1] = false;
  
    for(int i = 2; i < 100005; i++)
        prime[i] = true;
  
    for(int i = 2; i * i < 100005; i++) 
    {
        if (prime[i])
        {
            for(int j = i * i; j < 100005; j += i) 
            {
                prime[j] = false;
            }
        }
    }
}
  
// Function for finding smallest
// prime factors for every integer
static void smallestPrimeFactors()
{
    for(int i = 0; i < 100005; i++)
        spf[i] = -1;
          
    for(int i = 2; i * i < 100005; i++) 
    {
        for(int j = i; j < 100005; j += i)
        {
            if (spf[j] == -1) 
            {
                spf[j] = i;
            }
        }
    }
}
  
// Function to find the sum of
// prime factors of number
static int sumOfPrimeFactors(int n)
{
    int ans = 0;
    while (n > 1)
    {
  
        // Add smallest prime
        // factor to the sum
        ans += spf[n];
  
        // Reduce N
        n /= spf[n];
    }
  
    // Return the answer
    return ans;
}
  
// Function to return the length of
// sequence of for the given number
static int findLength(int n)
{
  
    // If the number is prime
    if (prime[n]) 
    {
        return 1;
    }
  
    // If a previously computed
    // subproblem occurred
    if (dp[n] != 0) 
    {
        return dp[n];
    }
  
    // Calculate the sum of
    // prime factors
    int sum = sumOfPrimeFactors(n);
  
    return dp[n] = 1 + findLength(sum);
}
  
// Function to return the maximum length
// of sequence for the given range
static int maxLength(int n, int m)
{
  
    // Pre-calculate primes
    sieve();
  
    // Precalculate smllest
    // prime factors
    smallestPrimeFactors();
  
    int ans = int.MinValue;
  
    // Iterate over the range
    for(int i = n; i <= m; i++)
    {
        if (i == 4)
        {
            continue;
        }
  
        // Update maximum length
        ans = Math.Max(ans, findLength(i));
    }
    return ans;
}
  
// Driver Code
public static void Main(String[] args)
{
    int n = 2, m = 14;
  
    Console.Write(maxLength(n, m));
}
}
  
// This code is contributed by 29AjayKumar 

chevron_right


Output: 

4

Time complexity: O((NlogN) 
Auxiliary Space: O(N)

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the DSA Self Paced Course at a student-friendly price and become industry ready.




My Personal Notes arrow_drop_up

Recommended Posts:


Check out this Author's contributed articles.

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.