You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
|
|
|
|
#include <bits/stdc++.h>
|
|
|
|
|
|
|
|
|
|
using namespace std;
|
|
|
|
|
const int N = 1e5 + 10;
|
|
|
|
|
/**
|
|
|
|
|
测试用例:
|
|
|
|
|
10 20 3
|
|
|
|
|
答案:
|
|
|
|
|
7
|
|
|
|
|
*/
|
|
|
|
|
|
|
|
|
|
//欧拉筛
|
|
|
|
|
int primes[N], cnt; // primes[]存储所有素数
|
|
|
|
|
bool st[N]; // st[x]存储x是否被筛掉
|
|
|
|
|
void get_primes(int n) {
|
|
|
|
|
for (int i = 2; i <= n; i++) {
|
|
|
|
|
if (!st[i]) primes[cnt++] = i;
|
|
|
|
|
for (int j = 0; primes[j]*i <= n; j++) {
|
|
|
|
|
st[primes[j] * i] = true;
|
|
|
|
|
if (i % primes[j] == 0) break;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//并查集数组
|
|
|
|
|
int fa[N];
|
|
|
|
|
|
|
|
|
|
//要深入理解这个递归并压缩的过程
|
|
|
|
|
int find(int x) {
|
|
|
|
|
if (fa[x] != x) fa[x] = find(fa[x]);
|
|
|
|
|
return fa[x];
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
//加入家族集合中
|
|
|
|
|
void join(int c1, int c2) {
|
|
|
|
|
int f1 = find(c1), f2 = find(c2);
|
|
|
|
|
if (f1 != f2)fa[f1] = f2;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
//读入一个开始和结束,a:开始,b:结束
|
|
|
|
|
int a, B, p, ans;
|
|
|
|
|
|
|
|
|
|
int main() {
|
|
|
|
|
//读入
|
|
|
|
|
cin >> a >> b >> p;
|
|
|
|
|
|
|
|
|
|
//并查集初始化
|
|
|
|
|
for (int i = a; i <= b; i++) fa[i] = i;
|
|
|
|
|
|
|
|
|
|
//筛出b以内的所有素数
|
|
|
|
|
get_primes(b);
|
|
|
|
|
|
|
|
|
|
//遍历筛出的质数表,找到每一个大于等于p的质数,然后把这个质数在y范围内的倍数找出来,并加入到动态数组v中
|
|
|
|
|
for (int i = 0; i < cnt; i++) {
|
|
|
|
|
if (primes[i] >= p) {
|
|
|
|
|
//将具有公共质数因子的数,放到一个数组v中
|
|
|
|
|
vector<int> v;
|
|
|
|
|
for (int j = 1; j * primes[i] <= b; j++)//找出质数倍数
|
|
|
|
|
if (j * primes[i] >= a && j * primes[i] <= b)
|
|
|
|
|
v.push_back(j * primes[i]);
|
|
|
|
|
//把数组v中的元素进行并查集关联
|
|
|
|
|
for (int j = 1; j < v.size(); j++)
|
|
|
|
|
join(v[j - 1], v[j]);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
//并查集个数
|
|
|
|
|
for (int i = a; i <= b; i++) if (fa[i] == i) ans++;
|
|
|
|
|
//输出
|
|
|
|
|
cout << ans << endl;
|
|
|
|
|
return 0;
|
|
|
|
|
}
|