求质数的五种方法,参考别人后总结滴。(新手)

本文介绍了四种求解1至n范围内质数的方法:最蠢办法、普通方法、埃拉托斯特尼筛法及欧拉筛法,并分析了各自的优缺点与时间复杂度。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

给定题目求 1~n的质数

1. 最蠢的办法

bool isprime(int n)
{
	int k = n;
	if (k == 1 || k == 0)return false;
	for (int i = 2; i < k; i++)
	{
		if (k%i == 0)
			return false;
	}
	return true;
}

这种方法应该只适合求比较小的数,当n为10000000时,那是相当费时间的。

2.普通方法

bool isprime(int n)
{
	int k = sqrt(n);
	if (k == 1 || k == 0)return false;
	for (int i = 2; i <= k; i++)
	{
		if (k%i == 0)
			return false;
	}
	return true;
}

因为是合数的话,就一定有一个小于sqrt(n)的因数(具体证明自行baidu),所以素数一定就没有。
虽然把n改成了sqrt(n)但是还是不够看啊,一般。

3.埃拉托斯特尼筛法

原理:核心就是素数的倍数不是素数,围绕这个思路来展开
:假设给定范围(a,b),我们从第一个素数2开始,删除所有2的倍数,直到2的倍数大于b时停止,然后从3的倍数开始删除,那现在轮到4了,但是4是2的倍数,所以4已经被删除了,所以跳到了5,一次类推,直到删的数是小于sqrt(b)的。
这里的表述有点变扭,毕竟也只是写给我自己看的,若是有人看到了,觉得不好也请见谅。

int* isprime=new int [100000001];//设定一个动态数组大一点
int a,b;
cin>>a>>b;
isprime[0]=isprime[1]=0;
for(int i=2;i<=b;i++)
    isprime[i]=1;//先将范围内的所有数都标记为素数;
for(int i=2;i<=sqrt(b);i++)
{
      if(isprime[i]==0)//如果这个数不是素数的话就continue
          continue;
      for(int j=i*i;j<=b;j+=i)
          isprime[j]=0;//将合数全部标记为0;
}

这也就是代码的核心部分,具体是要输出所有素数,还是判断,自由发挥。
时间复杂度为:O(nloglogn)

4. 欧拉筛法

vis[1]=1;
for (int i=2;i<=n;i++)
{
    if (!vis[i])
        pri[++tot]=i;
    for (int j=1;j<=tot;j++)
    {
        if (i*pri[j]>n) break;
        vis[i*pri[j]]=1;
        if (i%pri[j]==0) break;
    }
}

这里的if (i%pri[j]==0) break;比较关键
看了别人那么多解释,我是这样理解的:

5.打表法

就是将数据都算出来,然后存起来,之后直接用就可以了。我是这么理解的

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值