素数的求解

本文详细介绍了素数的定义以及如何判断一个数是否为素数,包括试除法及其优化策略。接着讨论了如何求解一定范围内的素数,如[1,n]之间的素数,以及求解N个素数和不小于n的最小素数的方法。内容涵盖了从基本的试除法到埃拉托斯特尼筛法,并涉及算法优化和存储策略。" 111732656,10295038,Dell PowerEdge 服务器RAID配置指南,"['Dell服务器', 'RAID技术', '服务器管理', '存储配置']

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

素数的定义

定义:在一个大于0的自然数中,除了1和此整数自身外,不能被其他自然数整除的数。

问题 1、判断一个数是否为素数

问题 2、求解[1,n]之间的素数

问题 3、求解 N 个素数。

问题 4、求解不小于n的最小素数

------------------------

问题 1、判断一个数是否为素数

思路<1> 试除法

思路<2> 试除法 + 抛去偶数

思路<3> 试除法 + 抛去偶数 + 缩小试除范围

思路<4> 对素数试除法 + 减少扫描区间

-----------------

思路(1) 试除法

基本思路:判断n是否为素数时,检查区间[2,n - 1]之间的数是否能整除n。

代码:

bool IsPrime(int nNum)
{
	for (int i = 2;i < nNum;i++)
	{
		if (nNum % i == 0)
		{
			return false;
		}
	}
	return true;
}

思路(2) 试除法 + 抛去偶数

具体思路:素数肯定是奇数,因为偶数肯定能被2整除,所以在检查区间[2,n - 1]之间的数时,只判断奇数是否能整除n即可。

代码:

///试除法 + 刨除偶数
bool IsPrime(int nNum)
{
	if (nNum == 2)//2是素数,直接返回
	{
		return true;
	}
	if ((nNum & 1) == 0)//刨除偶数
	{
		return false;
	}
	for (int i = 3;i < nNum;i += 2)
	{
		if (nNum % i == 0)
		{
			return false;
		}
	}
	return true;
}
注意:

(1)如果直接写for循环,那么上述代码就会错误的判断偶数为素数,因此需要把偶数单独处理,直接判断其是否为偶数。

(2)在单独处理偶数时,这里使用位操作进行做的,效率比取余操作高。

思路(3) 试除法 + 抛去偶数 + 缩小试除范围

具体思路:思路 1和思路 2的试除范围都在[2,n - 1],其实范围可以限制在[2,sqrt[n]],因为如果一个数不是素数,那么它肯定有至少有俩因子,而且因子也是成对出现的,而且一个因子是大于sqrt[n]的,一个因子是小于sqrt[n]的。

举例,100,可以分解为2 * 50、4 * 25、5 * 20、10 * 10

所以,对于每一对因子,我们只需要检查其小于sqrt[n]的因子即可,如果能整除,肯定也能被另一个因子整除。这样就能直接判断其是否能分解成成对的俩因子。

代码:

///试除法 + 刨除偶数 + 减少扫描区间
bool IsPrime(int nNum)
{
	if (nNum == 2)
	{
		return true;
	}
	if ((nNum & 1) == 0)//刨除偶数
	{
		return false;
	}
	for (int i = 3;i * i <= nNum;i += 2)
	{
		if (nNum % i == 0)
		{
			return false;
		}
	}
	return true;
}
思路(4) 对素数试除法 + 减少扫描区间

分析:

(1)合数(不是素数就是合数)是由若干个质数相乘而得来的,比如,合数6是有素数2和3相乘得到。15是由素数3和5相乘得到。

(2)前几个思路使用试除法时,也对合数进行了取余,所以造成浪费。比如判断103是否为素数时,如果采用

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值