Skip to content
Related Articles

Related Articles

Improve Article

Number of distinct ways to represent a number as sum of K unique primes

  • Last Updated : 15 Jun, 2021

Given an integer N, and an integer K, the task is to count the number of distinct ways to represent the number N as a sum of K unique primes.
Note: Distinct means, let N = 7 and K = 2, then the only way can be {2,5}, because {5,2} is same as {2,5}. So only 1 way.

Examples: 

Input: N = 10, K = 2
Output: 1
Explanation:
The only way is {3, 7} or {7, 3}

Input: N = 100, K = 5
Output: 55

Approach: The problem can be solved using Dynamic Programming and Sieve of Eratosthenes

  • Let dp[i][j][sum] be our 3D DP array, which stores the number of distinct ways to form a sum using j number of primes where the last index of prime selected is i in the prime vector. 
     
  • The prime numbers can be efficiently computed using Sieve of Eratosthenes. So, we can get a check of prime in O(1) time. 
     
  • Recurrence:

We can either include this current prime to our sum, or we can exclude it. 
dp[i][j][sum] = solve(i+1, j+1, sum+prime[i]) + solve(i+1, j, sum)

Below is the implementation of the above approach : 



C++




// C++ program to count the Number
// of distinct ways to represent
// a number as K different primes
#include <bits/stdc++.h>
using namespace std;
 
// Prime vector
vector<int> prime;
 
// Sieve array of prime
bool isprime[1000];
 
// DP array
int dp[200][20][1000];
 
void sieve()
{
    // Initialise all numbers
    // as prime
    memset(isprime, true,
        sizeof(isprime));
 
    // Sieve of Eratosthenes.
    for (int i = 2; i * i <= 1000;
        i++)
    {
        if (isprime[i])
        {
            for (int j = i * i;
                j <= 1000; j += i)
            {
                isprime[j] = false;
            }
        }
    }
    // Push all the primes into
    // prime vector
    for (int i = 2; i <= 1000; i++)
    {
        if (isprime[i])
        {
            prime.push_back(i);
        }
    }
}
 
// Function to get the number of
// distinct ways to get sum
// as K different primes
int CountWays(int i, int j, int sum,
        int n, int k)
{
 
    // If index went out of prime
    // array size or the sum became
    // larger than n return 0
    if (i > prime.size() || sum > n)
    {
        return 0;
    }
 
    // If sum becomes equal to n and
    // j becomes exactly equal to k.
    // Return 1, else if j is still
    // not equal to k, return 0
    if (sum == n) {
        if (j == k) {
            return 1;
        }
        return 0;
    }
 
    // If sum!=n and still j as
    // exceeded, return 0
    if (j == k)
        return 0;
 
    // If that state is already
    // calculated, return directly
    // the ans
    if (dp[i][j][sum])
        return dp[i][j][sum];
 
    int inc = 0, exc = 0;
    // Include the current prime
    inc = CountWays(i + 1, j + 1,
                sum + prime[i],
                n, k);
 
    // Exclude the current prime
    exc = CountWays(i + 1, j, sum,
                n, k);
 
    // Return by memoizing the ans
    return dp[i][j][sum] = inc + exc;
}
 
// Driver code
int main()
{
 
    // Precompute primes by sieve
    sieve();
 
    int N = 100, K = 5;
     
    cout << CountWays(0, 0, 0, N, K);
}

Java




// Java program to count the number
// of distinct ways to represent
// a number as K different primes
import java.io.*;
import java.util.*;
 
class GFG{
 
// Prime vector
static ArrayList<Integer> prime = new ArrayList<Integer>();
 
// Sieve array of prime
static boolean[] isprime = new boolean[1000];
 
// DP array
static int[][][] dp = new int[200][20][1000];
 
static void sieve()
{
     
    // Initialise all numbers
    // as prime
    for(int i = 0; i < 1000; i++)
        isprime[i] = true;
 
    //  Sieve of Eratosthenes.
    for(int i = 2; i * i < 1000; i++)
    {
        if (isprime[i])
        {
            for(int j = i * i;
                    j < 1000; j += i)
            {
                isprime[j] = false;
            }
        }
    }
     
    // Push all the primes into
    // prime vector
    for(int i = 2; i < 1000; i++)
    {
        if (isprime[i])
        {
            prime.add(i);
        }
    }
}
 
// Function to get the number of
// distinct ways to get sum
// as K different primes
static int CountWays(int i, int j, int sum,
                     int n, int k)
{
     
    // If index went out of prime
    // array size or the sum became
    // larger than n return 0
    if (i >= prime.size() - 1 || sum > n)
    {
        return 0;
    }
 
    // If sum becomes equal to n and
    // j becomes exactly equal to k.
    // Return 1, else if j is still
    // not equal to k, return 0
    if (sum == n)
    {
        if (j == k)
        {
            return 1;
        }
        return 0;
    }
 
    // If sum!=n and still j as
    // exceeded, return 0
    if (j == k)
        return 0;
 
    // If that state is already
    // calculated, return directly
    // the ans
    if (dp[i][j][sum] != 0)
        return dp[i][j][sum];
 
    int inc = 0, exc = 0;
    // Include the current prime
    inc = CountWays(i + 1, j + 1,
                  sum + prime.get(i),
                  n, k);
 
    // Exclude the current prime
    exc = CountWays(i + 1, j, sum, n, k);
 
    // Return by memoizing the ans
    return dp[i][j][sum] = inc + exc;
}
 
// Driver code
public static void main(String[] args)
{
 
    // Precompute primes by sieve
    sieve();
 
    int N = 100, K = 5;
 
    System.out.println(CountWays(0, 0, 0, N, K));
}
}
 
// This code is contributed by akhilsaini

Python3




# Python3 program to count the number
# of distinct ways to represent
# a number as K different primes
 
# Prime list
prime = []
 
# Sieve array of prime
isprime = [True] * 1000
 
# DP array
dp = [[['0' for col in range(200)]
            for col in range(20)]
            for row in range(1000)]
 
def sieve():
 
    #  Sieve of Eratosthenes.
    for i in range(2, 1000):
         
        if (isprime[i]):
            for j in range(i * i, 1000, i):
                isprime[j] = False
 
    # Push all the primes into
    # prime vector
    for i in range(2, 1000):
        if (isprime[i]):
            prime.append(i)
 
# Function to get the number of
# distinct ways to get sum
# as K different primes
def CountWays(i, j, sums, n, k):
 
    # If index went out of prime
    # array size or the sum became
    # larger than n return 0
    if (i >= len(prime) or sums > n):
        return 0
 
    # If sum becomes equal to n and
    # j becomes exactly equal to k.
    # Return 1, else if j is still
    # not equal to k, return 0
    if (sums == n):
        if (j == k):
            return 1
             
        return 0
 
    # If sum!=n and still j as
    # exceeded, return 0
    if j == k:
        return 0
 
    # If that state is already
    # calculated, return directly
    # the ans
    if dp[i][j][sums] == 0:
        return dp[i][j][sums]
 
    inc = 0
    exc = 0
     
    # Include the current prime
    inc = CountWays(i + 1, j + 1,
                 sums + prime[i],
                 n, k)
 
    # Exclude the current prime
    exc = CountWays(i + 1, j, sums, n, k)
 
    # Return by memoizing the ans
    dp[i][j][sums] = inc + exc
    return dp[i][j][sums]
 
# Driver code
if __name__ == "__main__":
     
    # Precompute primes by sieve
    sieve()
 
    N = 100
    K = 5
 
    print(CountWays(0, 0, 0, N, K))
 
# This code is contributed by akhilsaini

C#




// C# program to count the number
// of distinct ways to represent
// a number as K different primes
using System;
using System.Collections.Generic;
 
class GFG{
 
// Prime vector
static List<int> prime = new List<int>();
 
// Sieve array of prime
static bool[] isprime = new bool[1000];
 
// DP array
static int[, , ] dp = new int[200, 20, 1000];
 
static void sieve()
{
     
    // Initialise all numbers
    // as prime
    for(int i = 0; i < 1000; i++)
        isprime[i] = true;
 
    //  Sieve of Eratosthenes.
    for(int i = 2; i * i < 1000; i++)
    {
        if (isprime[i])
        {
            for(int j = i * i;
                    j < 1000; j += i)
            {
                isprime[j] = false;
            }
        }
    }
     
    // Push all the primes into
    // prime vector
    for(int i = 2; i < 1000; i++)
    {
        if (isprime[i])
        {
            prime.Add(i);
        }
    }
}
 
// Function to get the number of
// distinct ways to get sum
// as K different primes
static int CountWays(int i, int j, int sum,
                     int n, int k)
{
     
    // If index went out of prime
    // array size or the sum became
    // larger than n return 0
    if (i >= prime.Count - 1 || sum > n)
    {
        return 0;
    }
 
    // If sum becomes equal to n and
    // j becomes exactly equal to k.
    // Return 1, else if j is still
    // not equal to k, return 0
    if (sum == n)
    {
        if (j == k)
        {
            return 1;
        }
        return 0;
    }
 
    // If sum!=n and still j as
    // exceeded, return 0
    if (j == k)
        return 0;
 
    // If that state is already
    // calculated, return directly
    // the ans
    if (dp[i, j, sum] != 0)
        return dp[i, j, sum];
 
    int inc = 0, exc = 0;
     
    // Include the current prime
    inc = CountWays(i + 1, j + 1,
                  sum + prime[i], n, k);
 
    // Exclude the current prime
    exc = CountWays(i + 1, j, sum, n, k);
 
    // Return by memoizing the ans
    return dp[i, j, sum] = inc + exc;
}
 
// Driver code
static public void Main()
{
     
    // Precompute primes by sieve
    sieve();
 
    int N = 100, K = 5;
 
    Console.WriteLine(CountWays(0, 0, 0, N, K));
}
}
 
// This code is contributed by akhilsaini

Javascript




<script>
// Javascript program to count the Number
// of distinct ways to represent
// a number as K different primes
 
// Prime vector
var prime = []; 
 
// Sieve array of prime
var isprime = Array(1000).fill(true);
 
// DP array
var dp = Array.from(Array(200), ()=>Array(20));
for(var i =0; i<200; i++)
        for(var j =0; j<20; j++)
            dp[i][j] = new Array(1000).fill(0);
 
function sieve()
{
    // Initialise all numbers
    // as prime
 
    // Sieve of Eratosthenes.
    for (var i = 2; i * i <= 1000;
        i++)
    {
        if (isprime[i])
        {
            for (var j = i * i;
                j <= 1000; j += i)
            {
                isprime[j] = false;
            }
        }
    }
    // Push all the primes into
    // prime vector
    for (var i = 2; i <= 1000; i++)
    {
        if (isprime[i])
        {
            prime.push(i);
        }
    }
}
 
// Function to get the number of
// distinct ways to get sum
// as K different primes
function CountWays(i,  j, sum, n, k)
{
 
    // If index went out of prime
    // array size or the sum became
    // larger than n return 0
    if (i > prime.length || sum > n)
    {
        return 0;
    }
 
    // If sum becomes equal to n and
    // j becomes exactly equal to k.
    // Return 1, else if j is still
    // not equal to k, return 0
    if (sum == n) {
        if (j == k) {
            return 1;
        }
        return 0;
    }
 
    // If sum!=n and still j as
    // exceeded, return 0
    if (j == k)
        return 0;
 
    // If that state is already
    // calculated, return directly
    // the ans
    if (dp[i][j][sum])
        return dp[i][j][sum];
 
    var inc = 0, exc = 0;
    // Include the current prime
    inc = CountWays(i + 1, j + 1,
                sum + prime[i],
                n, k);
 
    // Exclude the current prime
    exc = CountWays(i + 1, j, sum,
                n, k);
 
    // Return by memoizing the ans
    return dp[i][j][sum] = inc + exc;
}
 
// Driver code
// Precompute primes by sieve
sieve();
var N = 100, K = 5;
document.write( CountWays(0, 0, 0, N, K));
 
 
</script>
Output: 
55

 

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.  To complete your preparation from learning a language to DS Algo and many more,  please refer Complete Interview Preparation Course.

In case you wish to attend live classes with experts, please refer DSA Live Classes for Working Professionals and Competitive Programming Live for Students.




My Personal Notes arrow_drop_up
Recommended Articles
Page :