素数的多种判断方法

首先,贴上素数的最基本定义:素数又称为质数(prime number),定义为在大于1的自然数中,除了1和它本身以外不再有其他因数的自然数(即只能被1和它自身整除的大于等于2的整数。


1.方法一:

#include<iostream>
using namespace std;

int main(){
    int n;
    cin>>n;
    if(n<2)
        cout<<"非素数"<<endl;   //小于2的数,肯定是非素数
    for(int i=2;i<=n-1;++i)
    {
        if(n%i == 0){
            cout<<"非素数"<<endl;
            return 0;
        }
            
    }
    cout<<"素数"<<endl;
    return 0;
}

解释:这是最基本的,也是效率最低的方法。对于一个自然数n来说,需要判断n-2次,时间复杂度为O(n)。但试想,用比n的一半还大的数来整除n,是不是肯定是无法整除的,所以比n的一半还大的数就不用再判断了,进行算法改进,如法二


2.方法二:

#include<iostream>

using namespace std;

int main(){
    int n;
    cin>>n;
    if(n<2)
        cout<<"非素数"<<endl;   
    for(int i=2;i<n/2+1;++i)    //只需要测试从2~n/2+1(n为奇数时候,测试的最后一个数是比n的一半还大的最接近的整数)
    {
        if(n%i == 0){
            cout<<"非素数"<<endl;
            return 0;
        }
            
    }
    cout<<"素数"<<endl;
    return 0;
}

解释:再进一步改进,如果一个数有因子的话,那么在这个数的平方根以内就应该有,否则就肯定没有因子。比如,36的平方根是6,那么在(i>=2 && i<=6)内,就必定有36的因子,所以36是非素数,再比如,99的平方根约为9.95,那么在(i>=2 && i<=9)内必定会有99的因子,所以99是非素数,再比如79,79的平方根约是8.89,在(i>=2 && i<=8)内没有能整除79的,所以79是素数,见方法三


3.方法三:

#include<iostream>
#include<cmath>

using namespace std;

int main(){
    int n;
    cin>>n;
    if(n<2)
        cout<<"非素数"<<endl;
    double sqrtm = sqrt(n*1.0);//声明一个浮点变量来保存根,i取值为小于sqrtm的最大整数
    for(int i=2;i<sqrtm;++i)    
    {
        if(n%i == 0){
            cout<<"非素数"<<endl;
            return 0;
        }
            
    }
    cout<<"素数"<<endl;
    return 0;
}

解释:当然,算法还可以进一步优化,我们知道,在有的自然数的偶数中,除了2之外,其他的偶数都是合数,都不是素数,所以,算法的关键部分还可以进行以下的修改:

in(n<2)   非素数

if(n==2)   素数

for(int i=3;i<sqrtm;i+=2)  //i从三开始,每次进行加2,调到下一个奇数进行判断。

      if(n%i == 0)

              非素数



4.方法四(筛选法):

用于计算并筛选一定范围内的素数


(1).C

#include<stdio.h>
#include<stdlib.h>
#include<math.h>

#define MAX 1000

int main(){
    int i,j;
    bool isPrime[MAX];
    for(i=2;i<=MAX;i++)
        isPrime[i] = 1;//一开始都假设为素数

    double sqrtm = sqrt(1001);
    for(i=2;i<sqrtm;i++)
        if(isPrime[i])
            for(j=i;i*j<MAX;++j)
                isPrime[i*j] = 0; //标记出非素数
    //自此,素数全部标记为1,非素数全部标记为0
    printf("素数:");
    for(i=2;i<=MAX;i++)
        if(isPrime[i] == 1)
            printf("%d,",i);
}


(2).C++.

#include<iostream>
#include<vector>
#include<fstream>
#include<cmath>

using namespace std;

int main(){
    vector<int> prime(5000,1); //一开始都标记为素数
    double sqrtm = sqrt(5000);
    for(int i=2;i<sqrtm;++i)
        if(prime[i])
            for(int j=i;i*j<5000;++j)
                prime[i*j] = 0;     //非素数标记为0
    ifstream in("d:\\a.txt");   //从文件读取数字以进行判断是否为素数
    for(int a;in>>a && a>1 && a<5000;)
        cout<<a<<" is "<<(prime[a]?"":"not ")<<" a prime.\n";
    return 0;
}





PS:还有不少方法,后续更新........



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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值