
Problem Statement
This problem requires determining the count of prime numbers that exist below a given integer n
. A prime number is a natural number greater than 1 that has no positive divisors other than 1 and itself. For a given integer n
, the task is to compute how many prime numbers are there which are strictly less than n
. This involves an efficient way to verify primality for numbers and count them up to n
.
Examples
Example 1
Input:
n = 10
Output:
4
Explanation:
There are 4 prime numbers less than 10, they are 2, 3, 5, 7.
Example 2
Input:
n = 0
Output:
0
Example 3
Input:
n = 1
Output:
0
Constraints
0 <= n <= 5 * 106
Approach and Intuition
In order to determine how many prime numbers are less than a given integer n
, we follow a systematic approach:
Understanding Primes: Recognize that prime numbers are those greater than 1 that are divisible only by 1 and themselves.
Use of Sieve of Eratosthenes: This is an efficient classical algorithm to generate all primes smaller than a given number n. It works by iteratively marking the multiples of each prime starting from 2.
Algorithm Steps:
- Create a list of boolean values initialized to
True
, corresponding to each number up ton-1
. - The value at position i represents whether the number i is a prime or not.
- Starting from the first prime number 2, mark all of its multiples as non-prime.
- Move to the next number and repeat if it is marked as True (prime). Continue this process up to sqrt(n), because a non-prime number will have at least one divisor less than or equal to sqrt(n).
- Finally, count all the
True
values in the list except for positions 0 and 1 (which represent 0 and 1, non-primes).
- Create a list of boolean values initialized to
Handling Special Cases: If
n
is 0 or 1, return 0 immediately as there are no numbers less than 2 that are prime.
This approach leverages the Sieve of Eratosthenes, optimizing primality testing for multiple numbers and is effective for large values of n
, up to the constraint maximum of 5 * 10^6
. By pre-computing the primes, previously marked non-prime numbers are skipped, reducing unnecessary calculations and ensuring that the operation completes in reasonable time for high values of n
.
Solutions
- C++
- Java
- Python
class Solution {
public:
int countPrimes(int n) {
if (n <= 2) {
return 0;
}
vector<bool> prime(n, true); // Mark all numbers as prime initially
for (int i = 2; i * i < n; i++) {
if (prime[i]) {
for (int j = i * i; j < n; j += i) {
prime[j] = false; // Mark as non-prime
}
}
}
int primeCount = 0;
for (int k = 2; k < n; k++) {
if (prime[k]) {
primeCount++; // Count primes
}
}
return primeCount;
}
};
Implement the "Count Primes" solution in C++ by using an optimized algorithm to determine the number of prime numbers less than a non-negative number ( n ). This algorithm leverages the Sieve of Eratosthenes method, which iteratively marks the multiples of each prime starting from 2 as non-prime.
Follow these steps to execute the solution effectively:
Start by handling the edge case: if ( n ) is less than or equal to 2, immediately return 0 as there are no prime numbers.
Initialize a boolean vector,
prime
, with all elements set totrue
. This vector represents the primality of numbers from 0 to ( n-1 ).Use a loop to traverse numbers starting from 2 up to the square root of ( n ). This is because any factor greater than the square root would have a corresponding factor less than the square root, effectively covering all numbers in the range without excess computation.
Inside the loop, if a number is marked as prime, iterate through its multiples starting from its square and mark them as non-prime in the vector. This is achieved using another loop which increments by the number itself, ensuring all multiples are marked.
After marking non-prime numbers, iterate through the vector to count the numbers that remain prime.
Return the count of prime numbers found.
This method is efficient due to its avoidance of redundant checks and minimal memory usage proportional to ( n ), ensuring a balance between time complexity and space usage. This approach significantly reduces the computational complexity compared to naive methods, especially for large values of ( n ). By meticulously marking non-primes through subsequent multiplications, major computations are limited to the necessary minimum.
class Solution {
public int primeCounter(int limit) {
if (limit <= 2) {
return 0;
}
boolean[] isComposite = new boolean[limit];
for (int current = 2; current <= (int) Math.sqrt(limit); ++current) {
if (!isComposite[current]) {
for (int multiple = current * current; multiple < limit; multiple += current) {
isComposite[multiple] = true;
}
}
}
int count = 0;
for (int index = 2; index < limit; index++) {
if (!isComposite[index]) {
count++;
}
}
return count;
}
}
The provided Java program efficiently counts the number of prime numbers less than a given number limit
. It uses the Sieve of Eratosthenes algorithm, which is an efficient way to identify prime numbers. Here's how the program operates:
- First, check if the input
limit
is less than or equal to 2. If true, return 0 because there are no prime numbers less than 2. - Initialize a boolean array
isComposite
to keep track of composite (non-prime) numbers. The size of this array islimit
, and by default, all entries are set tofalse
, indicating all numbers are initially assumed to be prime. - Iterate through numbers starting from 2 up to the square root of
limit
. For each numbercurrent
that has not been marked as composite:- Mark all multiples of
current
, starting fromcurrent*current
to less thanlimit
, as composite. The increment for marking composites iscurrent
, to skip directly to the next multiple.
- Mark all multiples of
- After marking the composites, count all numbers from 2 up to
limit
that are not marked as composite. Each unmarked number is a prime. - Return the total count of prime numbers.
By utilizing the Sieve of Eratosthenes, the algorithm efficiently avoids unnecessary computations, particularly with larger values of limit
, by reducing the number of multiples it checks and marking, thereby optimizing the overall counting process.
class Solution:
def prime_count(self, limit: int) -> int:
if limit <= 2:
return 0
is_prime = [False, False] + [True] * (limit - 2)
for current in range(2, int(sqrt(limit)) + 1):
if is_prime[current]:
for multiple in range(current * current, limit, current):
is_prime[multiple] = False
return sum(is_prime)
The problem "Count Primes" focuses on determining the number of prime numbers less than a non-negative number, limit
. The provided Python3 solution implements an efficient algorithm to solve this problem.
- Initialize the solution that checks for prime numbers up to a given limit. If the limit is 2 or less, the function directly returns 0 because there are no prime numbers less than 2.
- Manage a list
is_prime
initialized with boolean values. True signifies prime status. Specifically, positions corresponding to numbers 0 and 1 are set to False as they are not prime. - Utilize the Sieve of Eratosthenes algorithm:
- Iterate over each number starting from 2 up to the square root plus one of the limit. The square root comparison ensures optimizations in marking non-prime numbers.
- For each number found to still be marked as True (indicating it's a prime), mark its multiples as False (indicating they are not prime) starting from the square of the number (which is the smallest multiple that hasn’t already been marked from a lesser prime) up to the limit, incrementing by the number itself.
- Count and return all True values in the
is_prime
list which correspond to prime numbers.
This approach efficiently reduces the problem's complexity by not revisiting multiples of known primes and is well-suited for large values of limit
.
No comments yet.