Leetcode题目总结-Math-如何判断素数?
来源:互联网 发布:百度云总显示网络异常 编辑:程序博客网 时间:2024/06/06 09:04
今天做了一道很有意思的题目,leetcode上的204 Count primes.
题目:Count the number of prime numbers less than a non-negative number,n.
刚看到这道题目的时候,在想....小学生的题目,于是按照常规的判断方法即只能被1和本身这个数整除的数是素数。按照这个思路我写出了第一个解决方案。
My Solution1:
public int countPrimes(int n) { if(n == 0 || n == 1) return 0; //0和1不适素数 int count = 0;//纪录素数个数 boolean flag = true; //判断是否为素数的标志 for(int i = 2; i < n; i++ ){ //遍历n里面的所有数,来判断是否为素数 for(int j = 2; j < i; j++){ if(i%j == 0){ flag = false; break; } } if(flag) count ++; flag = true; } return count; }}
结果gg了,显示 time limit exceeded!
于是,想了想上述判断方法,明显存在效率极低的问题。对于每个数n,其实并不需要从2判断到n-1,我们知道,一个数若可以进行因数分解,那么分解时得到的两个数一定是一个小于等于sqrt(n),一个大于等于sqrt(n),据此,上述代码中并不需要遍历到n-1,遍历到sqrt(n)即可,因为若sqrt(n)左侧找不到约数,那么右侧也一定找不到约数。
My Solution2:
public int countPrimes(int n) { if(n == 0 || n == 1) return 0; int count = 0; boolean flag = true; for(int i = 2; i < n; i++ ){ for(int j = 2; j <= Math.sqrt(i);j++){ if(i%j == 0){ flag = false; break; } } if(flag) count ++; flag = true; } return count; }}
结果还是gg,time limit exceeded!
这就说明最开始的思路是不对的。没办法,百度了一下这道题目用到了一个算法 埃拉托色尼筛法算法。
下面介绍一下这个算法。
1)先把1删除(现今数学界1既不是质数也不是合数)
(2)读取队列中当前最小的数2,然后把2的倍数删去
(3)读取队列中当前最小的数3,然后把3的倍数删去
(4)读取队列中当前最小的数5,然后把5的倍数删去
(5)如上所述直到需求的范围内所有的数均删除或读取(即某个素数的平方等于最后一个数)
My Solution3:
public class Solution { public int countPrimes(int n) { if(n == 0 || n == 1) return 0; boolean[] notprime = new boolean[n]; // 默认所有的元素值都会设置成false; boolean的初始值为false notprime[0] = true; notprime[1] = true; //前两个数都不是素数 for(int i = 2; i * i < n; i++){ //当某个素数的平方等于或者大于n的时候,判断结束 if(!notprime[i]){ //如果I是素数,那么 for(int j = 2; i * j < n; j++){ notprime[i*j] = true; } } } int count = 0; for(boolean notP : notprime){ if(!notP) count++; } return count; }}
跑下来其实效率也不是很高,后面我发现有重复的地方:
for(int i = 2; i * i < n; i++){ if(!notprime[i]){ for(int j = 2; i * j < n; j++){ //这里有大量的数字重复,比如当i=2时候,j =2,3,...;当i=3是,j= 2,3,.. notprime[i*j] = true; //此时2*3在i = 2时候已经判断过; i = 3没有必要再判断。 } } }
改正为:
for(int i = 2; i * i < n; i++){ if(!notprime[i]){ for(int j = i; i * j < n; j++){ notprime[i*j] = true; } } }
这样就好了!!!!
阅读全文
0 0
- Leetcode题目总结-Math-如何判断素数?
- LeetCode之Math题目汇总
- 如何判断素数
- 判断素数的方法。 题目 素数对猜想 (20)
- 如何判断一个数素数
- LeetCode 题目总结
- LeetCode 题目总结/分类
- LeetCode 题目总结/分类
- LeetCode 题目总结/分类
- LeetCode题目总结/分类
- LeetCode 题目总结/分类
- LeetCode 题目总结/分类
- LeetCode 题目总结/分类
- LeetCode 题目总结/分类
- LeetCode 题目总结/分类
- leetcode题目总结<1>
- leetcode题目总结<2>
- leetcode题目总结<3>
- Linux命令:pwd,切换用户,切换宿主目录,.,..,-,相对路径绝对路径
- Linux下编程求绝对路径和读取目录
- js显示动态时间的方法
- 活了这么久,突然感觉像白开水
- HttpClient4.5.3设置代理(Proxy)访问目标地址
- Leetcode题目总结-Math-如何判断素数?
- Leetcode-19: Remove Nth Node From End of List
- 在Windows上安装Elasticsearch v5.4.2
- 子进程创建do_fork
- java 中 哪些异常必须声明并捕获,否则产生编译错误
- 欢迎使用CSDN-markdown编辑器
- Codeforces 839 D. Winter is here (莫比乌斯反演)
- request.getParameterMap
- java中Map,List与Set的区别