当前位置: 首页 > news >正文

质数、约数详解

质数

含义:除了1和他本身外,不能被其他自然数整数的数叫做质数,否则为合数

注:1既不是质数也不是合数

试除法判断素数

思想:对于一个数n,由于只有1和他本身能被整除,那么我们只用枚举2~n-1看是否出现被整除的情况,如果没有说明是素数

#include<bits/stdc++.h>
using namespace std;
int n;
int main(){int x;cin>>x;//特判1if(x==1){cout<<"No"<<endl;continue;}bool f=true;//暴力从2~x-1for(int i=2;i<=x-1;i++){if(x%i==0){f=false;break;}}if(f)cout<<"Yes"<<endl;else cout<<"No"<<endl;return 0;
}

如果对于一个数x,可以被n整除,商为y,那么n=x*y,设x<=y,那么我们只用枚举x,如果n可以被x整除,那么也可以被y整除。所以对于上面判断方法可以优化:只用看在前半部分的数能否被n整除即可

#include<bits/stdc++.h>
using namespace std;
int n;
int main(){int x;cin>>x;if(x==1){cout<<"No"<<endl;continue;}bool f=true;for(int i=2;i*i<=x;i++){if(x%i==0){f=false;break;}}if(f)cout<<"Yes"<<endl;else cout<<"No"<<endl;return 0;
}

那么上面的方法也有问题,如果i为1e9,那么ii就会发生溢出,不能和x比了。所以我们把ii<=x换为i<=x/i,这样就不会发生溢出了

#include<bits/stdc++.h>
using namespace std;
int n;
int main(){int x;cin>>x;if(x==1){cout<<"No"<<endl;continue;}bool f=true;for(int i=2;i<=x/i;i++){if(x%i==0){f=false;break;}}if(f)cout<<"Yes"<<endl;else cout<<"No"<<endl;return 0;
}

分解质因数

根据算术基本定理,不考虑排列顺序的情况下,每个正整数都能够以唯一的方式表示成它的质因数的乘积。

n = p 1 x 1 × p 2 x 2 × p 3 x 3 . . . × p n x n n=p_{1}^{x_{1} } \times p_{2}^{x_{2} } \times p_{3}^{x_{3} }... \times p_{n}^{x_{n} } n=p1x1×p2x2×p3x3...×pnxn

pi代表质因数,xi代表指数

那么我们将他的因数i从小到大枚举,如果可以整除i,那么我们就将x一直除以i到不能除为止,然后输出i和指数(除以i的次数),然后再继续枚举。由于在前面将所有的整除的因数都除了,可以保证后来所能整除的因数都为质因数。

进一步优化:枚举可以不用枚举到x-1,可以枚举到 x \sqrt{x} x ,相当于枚举了n=x*y,x<=y中的x。

并且可以证明对于x,只能有一因数大于 x \sqrt{x} x :运用反证法,如果有两个因数大于 x \sqrt{x} x ,那么相乘就大于x,不等于x。

到最后如果剩下的数>1,说明剩下的数是唯一一个大于 x \sqrt{x} x 的因数。

#include<bits/stdc++.h>
using namespace std;
int n;
int main(){int x;cin>>x;for(int i=2;i<=sqrt(x);i++){if(x%i==0){int ans=0;while(x%i==0){x/=i;ans++;}cout<<i<<" "<<ans<<endl;}}if(x>1)cout<<x<<" "<<1<<endl;cout<<endl;return 0;
}

埃式筛法筛质数

求出1~n中的所有质数的个数

时间复杂度O(nlog(logn))

思想:从2~n开始枚举,每次碰到素数记录一下,并且将他的倍数(合数)给筛掉,那么可以保证后面没有被筛掉的都是素数

	cin>>n;int con=0;for(int i=2;i<=n;i++){if(!st[i]){st[i]=true;prim[++con]=i;for(int j=i;j<=n;j+=i)st[j]=true;}}cout<<con;

约数

约数也叫因数,如果n能被m整除,那么m就叫做n的约数

试除法求约数

给定n个数ai,求每个数的约数,并从小到大排序输出

#include<bits/stdc++.h>
using namespace std;
int n;
const int N=1e6+10;
int prim[N];
bool st[N];
int main(){cin>>n;vector<int> v;while(n--){v.clear();int x;cin>>x;for(int i=1;i<=x/i;i++){if(x%i==0){v.push_back(i);if(x/i!=i)v.push_back(x/i);}}sort(v.begin(),v.end());for(int i=0;i<v.size();i++){cout<<v[i]<<" ";}cout<<endl;}return 0;
}

最大公约数

最大公约数:两个或多个整数共有约数中最大的一个数,也称最大公因数,最大公因子

用(a,b)表示a和b的最大公因数:有结论(a,b)=(a,ka+b),其中a、b、k都为自然数。

也就是说,两个数的最大公约数,将其中一个数加到另一个数上,得到的新数,其公约数不变.

那么我们就可以将(a,ka+b),通过(ka+b)%a的方式,变为b,那么就变为(a,b)了

基本思路就是取余,一直取到其中一个结果为0的时候就可以结束,剩下的一个数就是最大公约数

int gcd(int a,int b){return b?gcd(b,a%b):a;
}

http://www.mrgr.cn/news/16542.html

相关文章:

  • centOS服务器上如何安装宝塔面板-两分钟快速配置
  • 【web开发】Spring Boot 快速搭建Web项目(二)
  • 2024.8.29顺丰笔试算法题真题
  • PMNet
  • python网络爬虫(三)——爬虫攻防
  • 【算法】前缀和例题讲解
  • 基于STM32的智能物料运载小车:OpenMV和OpenCV结合图像识别与运动控制算法优化(代码示例)
  • diffusion 模型gguf量化使用案例,支持CPU运行
  • 代码改进
  • Claude3,Claude3.5最新开通教程及其优势,开启AI新时代的全能战士
  • Kaggle竞赛:Rossmann Store Sales第66名策略复现
  • 算法-最长连续序列
  • important vocabulary of noun - node
  • Unity编辑器扩展之Scene视图扩展
  • 【计算机组成原理】3.2.0+3.2.3 主存储器的基本组成
  • 基于asp.net的中小学选课系统源码access数据库
  • 怎么用AI做视频总结?
  • 2024/8/31 笔记
  • 链路聚合基础笔记
  • PMP–知识卡片--SCQA金字塔表达