Help Hanzo(LightOJ - 1197)(欧拉筛 + 思维)
LightOJ - 1197 Help Hanzo
来源:LightOJ - 1197 Help Hanzo
题意:
判断a ~ b区间内,有多少个素数,a,b范围[1, 2 ^ 31 - 1],b - a <= 1e5
思路:
这个题巧妙就巧妙在区间长度上,为1e5,而a,b最大范围为INT_MAX,所以可以先筛出来sqrt(INT_MAX) 以内的素数,约为50000,通过这些素数去标记[a, b]范围内的素数,通过 埃氏筛的方法(O(nloglogn)),将每一个素数增加,每次增加其本身的大小。
只需要筛出5e4个素数的原因:类似于对一个数质因数分解,当筛到素数p > sqrt(x)时结束,最后这个数如果大于1,那么它一定是素数,而1e5以内的最大素数的平方一定大于int的上限
那么如何标记呢?每次标记的起点又是什么呢?
- 标记:这里我们可以开一个数组,下标为0 ~ b - a + 1,分别对应a到b。
- 起点:记当前的素数为p,我们就通过a除以p向上取整的形式,获取第一个大于等于a的数是p的多少倍,将它作为起点,但是p本身我们是不想标记的,多以我们最小要从p的2倍开始标记,每次增加p即可。
注意:当a = 1的时候我们是无法通过素数将其标记的,所以需要特判一下
代码:
#include <bits/stdc++.h>
#define rep(i, n) for (int i = 1; i <= (n); ++i)
#define debug(a) cout << #a << " = " << a << endl;
using namespace std;
typedef long long ll;
const int M = 5e4 + 10;
const int N = 1e5 + 10;
ll a, b;
bool vis1[N];
int prime[M], cnt;
bool vis[M];
void init(int n) {//欧拉筛vis[0] = vis[1] = 1;for (int i = 2; i <= n; ++i) {if (!vis[i]) prime[cnt++] = i;for (int j = 0; i * prime[j] <= n; ++j) {vis[i * prime[j]] = 1;if (i % prime[j] == 0) break;}}
}
int main()
{init(M - 10);int t; cin >> t;for (int k = 1; k <= t; ++k) {scanf("%lld%lld", &a, &b);int l = b - a + 1;memset(vis1, 0, sizeof(bool) * l);// 指标记需要用到的,防止超时for (int i = 0; i < cnt; ++i) { //O(nloglog(n))ll p = prime[i];if (p > b) break;int j = 2;if (p < a) j = (a + p - 1) / p;while (p * j <= b) vis1[p * j - a] = 1, j++;}if (a == 1) vis1[0] = 1;//特判,将1标记为非素数int ans = 0;for (int i = 0; i < l; ++i)ans += !vis1[i];//没标记的 为素数printf("Case %d: %d\n", k, ans);}return 0;
}
END
Help Hanzo(LightOJ - 1197)(欧拉筛 + 思维)相关推荐
- cf 1062d 思维 欧拉筛变形
http://codeforces.com/contest/1062/problem/D 题意:给个n ,在n之内 所有(a,b) ,如果存在唯一的x 使a*|x| == b 或者 b* |x| == ...
- Help Hanzo LightOJ - 1197(素数筛法)
Help Hanzo LightOJ - 1197 题目链接: https://cn.vjudge.net/problem/26909/origin 题意: 求两个数a,b之间有多少个素数. 思路: ...
- 欧拉筛 筛法求素数 及其例题 时间复杂度O(n)
埃式筛法尽管不错,但是确实做了许多无用功,某个数可能会被重复的筛好几次,欧拉筛解决了这个方法,下面为代码: 注意理解if(i%prim[j]==0) break; 大佬讲的不错的博客,我就不做复读机了 ...
- 线性筛素数(欧拉筛)
欧拉筛是O(n)复杂度的筛素数算法,1秒内埃筛能处理1e6的数据,而1e7的数据就必须用欧拉筛了. 埃筛的基本思想是:素数的倍数一定是合数. 欧拉筛基本思想是:任何数与素数的乘积一定是合数 算法概述: ...
- 【数的专题】——欧拉筛
上题:https://www.luogu.org/problemnew/show/P3383 当你总是觉得筛质数太慢的时候,不妨来试一下欧拉筛: 基本原理: 设一个整数x,保证它只被它的最小质因子筛去 ...
- Enlarge GCD CodeForces - 1034A(欧拉筛+最大公约数)
题意: 给出n个数,删去其中一些使得总的gcd(最大公约数)最大 题目: Mr. F has n positive integers, a1,a2,-,an. He thinks the greate ...
- 【BZOJ2818】Gcd,数论练习之欧拉筛
传送门 写在前面:比较简单的数论题目了 思路:对i来说,所有与i互质的数和i都乘同一个质数p,那么得到的两个数的gcd一定是p,所以我们就可以利用这个来搞一搞了,对1-n的phi预处理出来(欧拉筛), ...
- 素数筛选法(埃氏筛 欧拉筛)
质数筛选法 文章目录 质数筛选法 前言 一.埃氏筛 O(nloglogn)O(nloglogn)O(nloglogn) 二.欧拉筛O(n)O(n)O(n) 总结 前言 当需要大范围内的素数时,例如1e ...
- 埃氏筛 线性筛(欧拉筛) 算法解析
埃氏晒 埃拉托斯特尼筛法,简称埃氏晒,是一种用来求自然数n以内的全部素数. 他的基本原理是,如果我们要获得小于n的所有素数,那就把不大于根号n的所有素数的倍数剔除. 埃氏晒的原理很容易理解,一个合数, ...
最新文章
- Button的使用(六):ToggleButton
- c# point偏移_GMap.NET开发技巧(四)-GPS百度地图坐标偏移及地图加偏和逆向纠偏解决方法和代码...
- PPT模板中的”书签”
- 0006-ZigZag Conversion(Z 字形变换)
- ubuntu14.04 源
- 怎样检测mysql5.5安装成功_64位wiN7系统中装配MySQL5.5.17(测试安装成功哦!)
- 信息学奥赛一本通C++语言——1068:与指定数字相同的数的个数
- 关于selenium关闭chrome密码登录时弹出的密码提示框
- Android 使用WakeLock
- Unity3D 广播星历与精密星历
- 二 docker安装ca证书
- 软件测试的概念与过程
- 3D房地产营销PPT模板
- 亲测苹果CMS简洁精美影视模板整站源码+带视频教程
- flying-saucer生成PDF
- 【BZOJ 1305】[CQOI2009]dance跳舞
- 深度学习评估指标之目标检测——(yolov5 可视化训练结果以及result.txt解析)
- Java+Servlet+JSP实现Web宠物诊所管理系统
- 解决qq安全防护更新进程总提示的方法
- 使用Hadoop MapReduce进行大数据分析