Given an array arr[] consisting of N positive integers and an integer K, the task is to find the maximum sum of array elements in a subarray having maximum sum of distinct prime factors in each K-length subarray.
Note: If there are multiple answers then print the sum of the original subarray having maximum sum.
Examples:
Input: arr[] = {1, 4, 2, 10, 3}, K = 3
Output: 16
Explanation:
All possible subarrays of length 3 are:
{1, 4, 2} ? having 0+1+1= 2 distinct prime factors
{4, 2, 10} ? having 1+1+2= 4 distinct prime factors. Sum = 16.
{2, 10, 3} ? having 1+1+2= 4 distinct prime factors. Sum = 15.
Therefore, maximum sum of K length subarrays with maximum distinct prime factors is 16.Input: arr[] = {10, 14, 12, 9, 16, 11}, K = 2
Output: 26
Naive Approach: The simplest approach is to generate all possible subarrays of length K from the given array and traverse each subarray and count distinct prime factors of its elements and compute their sums. Finally, print the maximum sum among subarrays having maximum count of distinct prime factors.
Time Complexity: O(N3 * sqrt(MAX)), where MAX is the maximum number present in the array.
Auxiliary Space: O(N * sqrt(MAX))
Efficient Approach: The optimal idea is to use Sieve of Eratosthenes and Sliding window technique to solve this problem. Follow the steps below to solve the problem:
- Initialize an array, say CountDsitinct[], to store the count of distinct prime factors up to a limit using sieve by incrementing the count of CountDistinct[] every time, while marking multiples of prime number as false.
- The sum of a subarray (or window) of size K can be obtained in constant time using the sum of the previous subarray (or window) of size K using Sliding window technique.
- Traverse the array arr[] and check which subarray has the maximum sum of distinct prime numbers.
- Finally, print the sum of the subarray or the sum of the original array having the maximum count of prime factors.
Below is the implementation of the above approach:
// C++ program for the above approach #include <bits/stdc++.h> using namespace std;
#define MAX 100001 // Function to print the sum of // subarray of length K having // maximum distinct prime factors int maxSum( int arr[], int N, int K)
{ // If K exceeds N
if (N < K) {
cout << "Invalid" ;
return -1;
}
// Stores the count of distinct primes
int CountDistinct[MAX + 1];
// True, if index 'i' is a prime
bool prime[MAX + 1];
// Initialize the count of factors
// to 0 and set all indices as prime
for ( int i = 0; i <= MAX; i++) {
CountDistinct[i] = 0;
prime[i] = true ;
}
for ( long long int i = 2; i <= MAX; i++) {
// If i is prime
if (prime[i] == true ) {
// Number is prime
CountDistinct[i] = 1;
// Count of factors of a prime number is 1
for ( long long int j = i * 2; j <= MAX;
j += i) {
// Increment CountDistinct as
// the factors of i
CountDistinct[j]++;
// Mark its multiple non-prime
prime[j] = false ;
}
}
}
// Compute sum of first K-length subarray
int Maxarr_sum = 0, DistPrimeSum = 0;
for ( int i = 0; i < K; i++) {
Maxarr_sum += arr[i];
DistPrimeSum += CountDistinct[arr[i]];
}
// Compute sums of remaining windows
// by removing first element of the
// previous window and adding last
// element of the current window
int curr_sum = DistPrimeSum;
int curr_arrSum = Maxarr_sum;
for ( int i = K; i < N; i++) {
curr_sum += CountDistinct[arr[i]]
- CountDistinct[arr[i - K]];
curr_arrSum += arr[i] - arr[i - K];
if (curr_sum > DistPrimeSum) {
DistPrimeSum = curr_sum;
Maxarr_sum = curr_arrSum;
}
else if (curr_sum == DistPrimeSum) {
Maxarr_sum = max(
curr_arrSum, Maxarr_sum);
}
}
// Print the maximum sum
cout << Maxarr_sum;
} // Driver Code int main()
{ // Given array
int arr[] = { 1, 4, 2, 10, 3 };
// Given size of subarray
int K = 3;
// Size of the array
int N = sizeof (arr) / sizeof (arr[0]);
maxSum(arr, N, K);
return 0;
} |
// Java Program to implement // the above approach import java.io.*;
import java.util.*;
class GFG
{ static int MAX = 100001 ;
// Function to print the sum of
// subarray of length K having
// maximum distinct prime factors
static void maxSum( int arr[], int N, int K)
{
// If K exceeds N
if (N < K) {
System.out.println( "Invalid" );
return ;
}
// Stores the count of distinct primes
int CountDistinct[] = new int [MAX + 1 ];
// True, if index 'i' is a prime
boolean prime[] = new boolean [MAX + 1 ];
// Initialize the count of factors
// to 0 and set all indices as prime
for ( int i = 0 ; i <= MAX; i++) {
CountDistinct[i] = 0 ;
prime[i] = true ;
}
for ( int i = 2 ; i <= MAX; i++) {
// If i is prime
if (prime[i] == true ) {
// Number is prime
CountDistinct[i] = 1 ;
// Count of factors of a prime number is 1
for ( int j = i * 2 ; j <= MAX; j += i) {
// Increment CountDistinct as
// the factors of i
CountDistinct[j]++;
// Mark its multiple non-prime
prime[j] = false ;
}
}
}
// Compute sum of first K-length subarray
int Maxarr_sum = 0 , DistPrimeSum = 0 ;
for ( int i = 0 ; i < K; i++) {
Maxarr_sum += arr[i];
DistPrimeSum += CountDistinct[arr[i]];
}
// Compute sums of remaining windows
// by removing first element of the
// previous window and adding last
// element of the current window
int curr_sum = DistPrimeSum;
int curr_arrSum = Maxarr_sum;
for ( int i = K; i < N; i++) {
curr_sum += CountDistinct[arr[i]]
- CountDistinct[arr[i - K]];
curr_arrSum += arr[i] - arr[i - K];
if (curr_sum > DistPrimeSum) {
DistPrimeSum = curr_sum;
Maxarr_sum = curr_arrSum;
}
else if (curr_sum == DistPrimeSum) {
Maxarr_sum
= Math.max(curr_arrSum, Maxarr_sum);
}
}
// Print the maximum sum
System.out.println(Maxarr_sum);
}
// Driver Code
public static void main(String[] args)
{
// Given array
int arr[] = { 1 , 4 , 2 , 10 , 3 };
// Given size of subarray
int K = 3 ;
// Size of the array
int N = arr.length;
maxSum(arr, N, K);
}
} // This code is contributed by Kingash. |
# Python3 program for the above approach import math
MAX = 100001
# Function to print the sum of # subarray of length K having # maximum distinct prime factors def maxSum(arr, N, K):
# If K exceeds N
if (N < K):
print ( "Invalid" )
return - 1
# Stores the count of distinct primes
CountDistinct = [ 0 ] * ( MAX + 1 )
# True, if index 'i' is a prime
prime = [ 0 ] * ( MAX + 1 )
# Initialize the count of factors
# to 0 and set all indices as prime
for i in range ( 0 , MAX + 1 ):
CountDistinct[i] = 0
prime[i] = True
for i in range ( 2 , MAX + 1 ):
# If i is prime
if (prime[i] = = True ):
# Number is prime
CountDistinct[i] = 1
# Count of factors of a prime number is 1
for j in range (i * 2 , MAX + 1 ,i):
# Increment CountDistinct as
# the factors of i
CountDistinct[j] + = 1
# Mark its multiple non-prime
prime[j] = False
# Compute sum of first K-length subarray
Maxarr_sum,DistPrimeSum = 0 , 0
for i in range ( 0 ,K):
Maxarr_sum + = arr[i]
DistPrimeSum + = CountDistinct[arr[i]]
# Compute sums of remaining windows
# by removing first element of the
# previous window and adding last
# element of the current window
curr_sum = DistPrimeSum
curr_arrSum = Maxarr_sum
for i in range (K,N):
curr_sum + = CountDistinct[arr[i]] - CountDistinct[arr[i - K]]
curr_arrSum + = arr[i] - arr[i - K]
if (curr_sum > DistPrimeSum):
DistPrimeSum = curr_sum
Maxarr_sum = curr_arrSum
elif (curr_sum = = DistPrimeSum):
Maxarr_sum = max (curr_arrSum, Maxarr_sum)
print (Maxarr_sum)
# Driver Code # Given array arr = [ 1 , 4 , 2 , 10 , 3 ]
# Given size of subarray K = 3
# Size of the array N = len (arr)
maxSum(arr, N, K) # This code is contributed by shinjanpatra |
// C# Program to implement // the above approach using System;
public class GFG
{ static int MAX = 100001;
// Function to print the sum of
// subarray of length K having
// maximum distinct prime factors
static void maxSum( int []arr, int N, int K)
{
// If K exceeds N
if (N < K) {
Console.WriteLine( "Invalid" );
return ;
}
// Stores the count of distinct primes
int []CountDistinct = new int [MAX + 1];
// True, if index 'i' is a prime
bool []prime = new bool [MAX + 1];
// Initialize the count of factors
// to 0 and set all indices as prime
for ( int i = 0; i <= MAX; i++) {
CountDistinct[i] = 0;
prime[i] = true ;
}
for ( int i = 2; i <= MAX; i++) {
// If i is prime
if (prime[i] == true ) {
// Number is prime
CountDistinct[i] = 1;
// Count of factors of a prime number is 1
for ( int j = i * 2; j <= MAX; j += i) {
// Increment CountDistinct as
// the factors of i
CountDistinct[j]++;
// Mark its multiple non-prime
prime[j] = false ;
}
}
}
// Compute sum of first K-length subarray
int Maxarr_sum = 0, DistPrimeSum = 0;
for ( int i = 0; i < K; i++) {
Maxarr_sum += arr[i];
DistPrimeSum += CountDistinct[arr[i]];
}
// Compute sums of remaining windows
// by removing first element of the
// previous window and adding last
// element of the current window
int curr_sum = DistPrimeSum;
int curr_arrSum = Maxarr_sum;
for ( int i = K; i < N; i++) {
curr_sum += CountDistinct[arr[i]]
- CountDistinct[arr[i - K]];
curr_arrSum += arr[i] - arr[i - K];
if (curr_sum > DistPrimeSum) {
DistPrimeSum = curr_sum;
Maxarr_sum = curr_arrSum;
}
else if (curr_sum == DistPrimeSum) {
Maxarr_sum
= Math.Max(curr_arrSum, Maxarr_sum);
}
}
// Print the maximum sum
Console.WriteLine(Maxarr_sum);
}
// Driver Code
public static void Main(String[] args)
{
// Given array
int []arr = { 1, 4, 2, 10, 3 };
// Given size of subarray
int K = 3;
// Size of the array
int N = arr.Length;
maxSum(arr, N, K);
}
} // This code is contributed by 29AjayKumar |
<script> // Javascript program for the above approach let MAX = 100001 // Function to print the sum of // subarray of length K having // maximum distinct prime factors function maxSum(arr, N, K)
{ // If K exceeds N
if (N < K) {
document.write( "Invalid" );
return -1;
}
// Stores the count of distinct primes
let CountDistinct = new Array(MAX + 1);
// True, if index 'i' is a prime
let prime = new Array(MAX + 1);
// Initialize the count of factors
// to 0 and set all indices as prime
for (let i = 0; i <= MAX; i++) {
CountDistinct[i] = 0;
prime[i] = true ;
}
for (let i = 2; i <= MAX; i++) {
// If i is prime
if (prime[i] == true ) {
// Number is prime
CountDistinct[i] = 1;
// Count of factors of a prime number is 1
for (let j = i * 2; j <= MAX;
j += i) {
// Increment CountDistinct as
// the factors of i
CountDistinct[j]++;
// Mark its multiple non-prime
prime[j] = false ;
}
}
}
// Compute sum of first K-length subarray
let Maxarr_sum = 0, DistPrimeSum = 0;
for (let i = 0; i < K; i++) {
Maxarr_sum += arr[i];
DistPrimeSum += CountDistinct[arr[i]];
}
// Compute sums of remaining windows
// by removing first element of the
// previous window and adding last
// element of the current window
let curr_sum = DistPrimeSum;
let curr_arrSum = Maxarr_sum;
for (let i = K; i < N; i++) {
curr_sum += CountDistinct[arr[i]]
- CountDistinct[arr[i - K]];
curr_arrSum += arr[i] - arr[i - K];
if (curr_sum > DistPrimeSum) {
DistPrimeSum = curr_sum;
Maxarr_sum = curr_arrSum;
}
else if (curr_sum == DistPrimeSum) {
Maxarr_sum = Math.max(curr_arrSum, Maxarr_sum);
}
}
// Print the maximum sum
document.write(Maxarr_sum);
} // Driver Code // Given array let arr = [ 1, 4, 2, 10, 3 ]; // Given size of subarray let K = 3; // Size of the array let N = arr.length maxSum(arr, N, K); </script> |
16
Time Complexity: O(N * log N)
Auxiliary Space: O(N)