Exactly n distinct prime factor numbers from a to b
Last Updated :
30 Jun, 2021
You are given two numbers a and b (1 <= a,b <= 10^8 ) and n. The task is to find all numbers between a and b inclusively having exactly n distinct prime factors. The solution should be designed in a way that it efficiently handles multiple queries for different values of a and b like in Competitive Programming.
Examples:
Input : a = 1, b = 10, n = 2
Output : 2
// Only 6 = 2*3 and 10 = 2*5 have exactly two
// distinct prime factors
Input : a = 1, b = 100, n = 3
Output: 8
// only 30 = 2*3*5, 42 = 2*3*7, 60 = 2*2*3*5, 66 = 2*3*11,
// 70 = 2*5*7, 78 = 2*3*13, 84 = 2*2*3*7 and 90 = 2*3*3*5
// have exactly three distinct prime factors
This problem is basically application of segmented sieve. As we know that all prime factors of a number are always less than or equal to square root of number i.e; sqrt(n). So we generate all prime numbers less than or equals to 10^8 and store them in an array. Now using this segmented sieve we check each number from a to b to have exactly n prime factors.
C++
#include<bits/stdc++.h>
using namespace std;
vector < int > primes;
void segmentedSieve()
{
int n = 10000;
int nNew = (n-2)/2;
bool marked[nNew + 1];
memset (marked, false , sizeof (marked));
for ( int i=1; i<=nNew; i++)
for ( int j=i; (i + j + 2*i*j) <= nNew; j++)
marked[i + j + 2*i*j] = true ;
primes.push_back(2);
for ( int i=1; i<=nNew; i++)
if (marked[i] == false )
primes.push_back(2*i+1);
}
int Nfactors( int a, int b, int n)
{
segmentedSieve();
int result = 0;
for ( int i=a; i<=b; i++)
{
int tmp = sqrt (i), copy = i;
int count = 0;
for ( int j=0; primes[j]<=tmp; j++)
{
if (copy%primes[j]==0)
{
count++;
while (copy%primes[j]==0)
copy = copy/primes[j];
}
}
if (copy != 1)
count++;
if (count==n)
result++;
}
return result;
}
int main()
{
int a = 1, b = 100, n = 3;
cout << Nfactors(a, b, n);
return 0;
}
|
Java
import java.util.*;
class GFG
{
static ArrayList<Integer> primes = new ArrayList<Integer>();
static void segmentedSieve()
{
int n = 10000 ;
int nNew = (n - 2 )/ 2 ;
boolean [] marked= new boolean [nNew + 1 ];
for ( int i = 1 ; i <= nNew; i++)
for ( int j = i; (i + j + 2 * i * j) <= nNew; j++)
marked[i + j + 2 * i * j] = true ;
primes.add( 2 );
for ( int i = 1 ; i <= nNew; i++)
if (marked[i] == false )
primes.add( 2 * i + 1 );
}
static int Nfactors( int a, int b, int n)
{
segmentedSieve();
int result = 0 ;
for ( int i = a; i <= b; i++)
{
int tmp = ( int )Math.sqrt(i), copy = i;
int count = 0 ;
for ( int j = 0 ; primes.get(j) <= tmp; j++)
{
if (copy % primes.get(j) == 0 )
{
count++;
while (copy % primes.get(j) == 0 )
copy = copy/primes.get(j);
}
}
if (copy != 1 )
count++;
if (count == n)
result++;
}
return result;
}
public static void main (String[] args)
{
int a = 1 , b = 100 , n = 3 ;
System.out.println(Nfactors(a, b, n));
}
}
|
Python3
import math
primes = [];
def segmentedSieve():
n = 10000 ;
nNew = int ((n - 2 ) / 2 );
marked = [ False ] * (nNew + 1 );
for i in range ( 1 , nNew + 1 ):
j = i;
while ((i + j + 2 * i * j) < = nNew):
marked[i + j + 2 * i * j] = True ;
j + = 1 ;
primes.append( 2 );
for i in range ( 1 , nNew + 1 ):
if (marked[i] = = False ):
primes.append( 2 * i + 1 );
def Nfactors(a, b, n):
segmentedSieve();
result = 0 ;
for i in range (a, b + 1 ):
tmp = math.sqrt(i);
copy = i;
count = 0 ;
j = 0 ;
while (primes[j] < = tmp):
if (copy % primes[j] = = 0 ):
count + = 1 ;
while (copy % primes[j] = = 0 ):
copy = (copy / / primes[j]);
j + = 1 ;
if (copy ! = 1 ):
count + = 1 ;
if (count = = n):
result + = 1 ;
return result;
a = 1 ;
b = 100 ;
n = 3 ;
print (Nfactors(a, b, n));
|
C#
using System;
using System.Collections;
class GFG
{
static ArrayList primes = new ArrayList();
static void segmentedSieve()
{
int n = 10000;
int nNew = (n - 2) / 2;
bool [] marked = new bool [nNew + 1];
for ( int i = 1; i <= nNew; i++)
for ( int j = i;
(i + j + 2 * i * j) <= nNew; j++)
marked[i + j + 2 * i * j] = true ;
primes.Add(2);
for ( int i = 1; i <= nNew; i++)
if (marked[i] == false )
primes.Add(2 * i + 1);
}
static int Nfactors( int a, int b, int n)
{
segmentedSieve();
int result = 0;
for ( int i = a; i <= b; i++)
{
int tmp = ( int )Math.Sqrt(i), copy = i;
int count = 0;
for ( int j = 0; ( int )primes[j] <= tmp; j++)
{
if (copy % ( int )primes[j] == 0)
{
count++;
while (copy % ( int )primes[j] == 0)
copy = copy / ( int )primes[j];
}
}
if (copy != 1)
count++;
if (count == n)
result++;
}
return result;
}
public static void Main()
{
int a = 1, b = 100, n = 3;
Console.WriteLine(Nfactors(a, b, n));
}
}
|
PHP
<?php
$primes = array ();
function segmentedSieve()
{
global $primes ;
$n = 10000;
$nNew = (int)(( $n -2)/2);
$marked = array_fill (0, $nNew + 1, false);
for ( $i = 1; $i <= $nNew ; $i ++)
for ( $j = $i ;
( $i + $j + 2 * $i * $j ) <= $nNew ; $j ++)
$marked [ $i + $j + 2 * $i * $j ] = true;
array_push ( $primes , 2);
for ( $i = 1; $i <= $nNew ; $i ++)
if ( $marked [ $i ] == false)
array_push ( $primes , 2 * $i + 1);
}
function Nfactors( $a , $b , $n )
{
global $primes ;
segmentedSieve();
$result = 0;
for ( $i = $a ; $i <= $b ; $i ++)
{
$tmp = sqrt( $i );
$copy = $i ;
$count = 0;
for ( $j = 0; $primes [ $j ] <= $tmp ; $j ++)
{
if ( $copy % $primes [ $j ] == 0)
{
$count ++;
while ( $copy % $primes [ $j ] == 0)
$copy = (int)( $copy / $primes [ $j ]);
}
}
if ( $copy != 1)
$count ++;
if ( $count == $n )
$result ++;
}
return $result ;
}
$a = 1;
$b = 100;
$n = 3;
print (Nfactors( $a , $b , $n ));
?>
|
Javascript
<script>
let primes = [];
function segmentedSieve()
{
let n = 10000;
let nNew = parseInt((n - 2) / 2, 10);
let marked = new Array(nNew + 1);
marked.fill( false );
for (let i = 1; i <= nNew; i++)
for (let j = i;
(i + j + 2 * i * j) <= nNew; j++)
marked[i + j + 2 * i * j] = true ;
primes.push(2);
for (let i = 1; i <= nNew; i++)
if (marked[i] == false )
primes.push(2 * i + 1);
}
function Nfactors(a, b, n)
{
segmentedSieve();
let result = 0;
for (let i = a; i <= b; i++)
{
let tmp = parseInt(Math.sqrt(i), 10), copy = i;
let count = 0;
for (let j = 0; primes[j] <= tmp; j++)
{
if (copy % primes[j] == 0)
{
count++;
while (copy % primes[j] == 0)
copy = parseInt(copy / primes[j], 10);
}
}
if (copy != 1)
count++;
if (count == n)
result++;
}
return result;
}
let a = 1, b = 100, n = 3;
document.write(Nfactors(a, b, n));
</script>
|
Output:
8
If you have another approach to solve this problem then please share in comments.
Like Article
Suggest improvement
Share your thoughts in the comments
Please Login to comment...