204 count prime

超时解法:

一个个判断,肯定会超

 

常规解法:建立Boolean数组判断下标对应的数字是否为质数,不是的话为true,是的话为false

采用的思想为the Sieve of Eratosthenes,由小到大将一个数(>1等于1没必要,相当于比自身)的倍数标记为非质数。最下面一个也是这种思想。

public int countPrimes(int n){
        boolean[] notPrime= new boolean[n];
        int count= 0;
        int loop= (int)Math.sqrt(n);
        for(int i=2; i<n; i++){
            if(!notPrime[i]){
                count++;
            }
            for(int j=2; i*j<n && i<=loop; j++){
                notPrime[i*j]= true;
            }
        }
        return count;
    }

 

大神的解法:https://leetcode.com/problems/count-primes/discuss/57593/12-ms-Java-solution-modified-from-the-hint-method-beats-99.95

原理大概是:

1. 大于2的偶数肯定不可能是质数,同时1也不是质数,所以初始判断质数的个数最多为n/2;

2. 1 2 3 4 5 6 7 8在n=【3,8】时质数的个数都符合规律n/2,故从9开始只判断奇数是否为质数即可。

public int countPrimes(int n) {
        if (n < 3)
            return 0;
            
        boolean[] f = new boolean[n];
        //Arrays.fill(f, true); boolean[] are initialed as false by default
        int count = n / 2;
        for (int i = 3; i * i < n; i += 2) {
            if (f[i])
                continue;
            
            for (int j = i * i; j < n; j += 2 * i) {//由于一开始并没有将偶数索引标记为true,直接将他们的数量减去了,故该处判断要跳过偶数
                if (!f[j]) {
                    --count;
                    f[j] = true;
                }
            }
        }
        return count;
    }

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值