计算范围内素数的 C++ 程序
给定一个范围 [L, R],我们需要找到范围 [L, R] 中素数总数的计数,其中 0 <= L <= R < 10000。考虑到有大量查询不同的范围。
例子:
Input : Query 1 : L = 1, R = 10
Query 2 : L = 5, R = 10
Output : 4
2
Explanation
Primes in the range L = 1 to R = 10 are
{2, 3, 5, 7}. Therefore for query, answer
is 4 {2, 3, 5, 7}.
For the second query, answer is 2 {5, 7}.
一个简单的解决方案是对每个查询 [L, R] 执行以下操作。从 L 遍历到 R,检查当前数字是否为素数。如果是,则增加计数。最后,返回计数。
一个有效的解决方案是使用埃拉托色尼筛法找出所有达到给定极限的素数。然后我们计算一个前缀数组来存储计数,直到限制之前的每个值。一旦我们有了前缀数组,我们就可以在 O(1) 时间内回答查询。我们只需要返回前缀[R] – 前缀[L-1]。
C++
// CPP program to answer queries for count of
// primes in given range.
#include
using namespace std;
const int MAX = 10000;
// prefix[i] is going to store count of primes
// till i (including i).
int prefix[MAX + 1];
void buildPrefix()
{
// Create a boolean array "prime[0..n]". A
// value in prime[i] will finally be false
// if i is Not a prime, else true.
bool prime[MAX + 1];
memset(prime, true, sizeof(prime));
for (int p = 2; p * p <= MAX; p++) {
// If prime[p] is not changed, then
// it is a prime
if (prime[p] == true) {
// Update all multiples of p
for (int i = p * 2; i <= MAX; i += p)
prime[i] = false;
}
}
// Build prefix array
prefix[0] = prefix[1] = 0;
for (int p = 2; p <= MAX; p++) {
prefix[p] = prefix[p - 1];
if (prime[p])
prefix[p]++;
}
}
// Returns count of primes in range from L to
// R (both inclusive).
int query(int L, int R)
{
return prefix[R] - prefix[L - 1];
}
// Driver code
int main()
{
buildPrefix();
int L = 5, R = 10;
cout << query(L, R) << endl;
L = 1, R = 10;
cout << query(L, R) << endl;
return 0;
}
输出:
2
4
有关详细信息,请参阅有关 Count Primes in Ranges 的完整文章!