数学知识.1

1.质数:在大于1的整数中,只包含1和本身这两个约数,就被称为质数,或者素数。

1) 质数的判定 -试除法

bool is_prime(int x)
{	
	if(x<2) return false;
	for(int p=2;p<x/p;p++)
		if(x%p==0) return false;
	return true;
}

试题:AcWing 866. 试除法判定质数 

2) 分解质因数

void divide (int x)
{
	for(int p=2;p<=x/p;p++) // 写成p<=x/p 的原因是 防止数据溢出 
	{
		if(x%p==0)
		{
			int s=0;
			while(x%p==0)
			{
				x/=p;
				s++;
			}
			cout<<p<<" "<<s<<endl;
		}
	}
	if(x>1) cout<<x<<" "<<"1"<<endl; // 最多存在一个大于x 的质因子 如果 有两个那么相乘大于x 了 显然不成立  
}

试题:AcWing 867. 分解质因数

3)质数筛选 

        1.埃氏筛法 

        

void isprime(int x) // cnt 为质数个数
{
	for(long long p=2;p<=x;p++)
	{
		for(long long i=p*p;i<=x;i+=p)
		{
			if(!st[i]) st[i]=true;
		}
		if(!st[p]) primes[cnt++]=p;
	}
}

        2.欧拉筛

void get_prime(long long x)
{
	for(long long p=2;p<=x;p++)
	{
		if(!st[p]) prime[cnt++]=p;
		for(long long s=0;prime[s]<=x/p;s++)
		{
			st[prime[s]*p]=true;// 用最小的质因子筛去合数 
			if(p%prime[s]==0) break;// 1)当p%prime[s] !=0 的时候 prime[s] 不是 p 的最小质因子,只能是ps*p的最小质因子
// 2)当p%prime[s] ==0 的时候,prime[s]  是 p 的最小质因子,接下来用prime[s+1] 筛去prime[s+1]*p
但是 prime[s]<prime[s+1] 所以最小质因子 应该为prime[s] 避免重复筛去 退出循环 
		}
	}
}

试题:AcWing 868. 筛质数

2.约数

约数的定义:如果一个整数能被两个整数整除,那么这两个数就是这个数的约数。

1)试除法求一个数的所有约数 

试题:AcWing 869. 试除法求约数

vector<int> solve(int x)
{
    vector<int>a;
    for(int p=1;p<=x/p;p++)
    {
        if(x%p==0)
        {
            a.push_back(p);
            if(p!=x/p)a.push_back(x/p);// 例如 4 / 2 =2 会放入 两个相同的元素 
        }
    }
    return a;
}

2)约数个数

公式:

 试题:AcWing 870. 约数个数 

#include <iostream>
#include <unordered_map> // 约数个数 (a1+1)*(a2+1)*(a3+1)···*(an+1); 
using namespace std;
const int N =100010;
const long long mod=1e9+7;
unordered_map<int,int>primes;
void solve(int x)
{
	for(int p=2;p<=x/p;p++)
	{
		while(x%p==0)
		{
			x/=p;
			primes[p]++;
		}
	}
	if(x>1) primes[x]++;
}

int main()
{
	int n;
	cin>>n;
	int x;
	while(n--)
	{	
		cin>>x;
		solve(x);
	}
	long long ans=1;
	for(auto prime:primes) ans=ans*(prime.second+1)%mod;//  在计算的时候取模 防止 爆数据 
	cout<<ans<<endl;
	return 0;
}

3)约数之和

公式:

 试题:AcWing 871. 约数之和 

#include <iostream>
#include <unordered_map>// 约数之和(p0+p1+`````+pn2)*(p1+````pn1)*````*(p1+````+pnn) 
using namespace std;
unordered_map<int,int>primes;
const int mod =1e9+7;
void solve(int x)
{
	for(int p=2;p<=x/p;p++)
	{
		while(x%p==0)
		{
			x/=p;
			primes[p]++;
		}
	}
	if(x>1) primes[x]++;
}

int main()
{
	int n;
	cin>>n;
	int x;
	while(n--)
	{
		cin>>x;
		solve(x);
	}
	long long ans=1;
	for(auto prime:primes)
	{
		int p=prime.first;int a=prime.second;
		long long t=1;
		while(a--) t=(p*t+1)%mod; // 求 (p0+p1+`````+pn2)*(p1+````pn1)*````*(p1+````+pnn)  技巧 
		ans=ans*t%mod;
	}
	cout<<ans<<endl;
}

 3.gcd(辗转相除法)

int gcd(int a,int b)// 一行代码 gcd 
{
	return b?gcd(b,a%b):a; // 三目运算符的用法 ':'前面是否问真,若真 执行':' 后面 ‘:’ 前面,否则 执行‘;’后面 
}

试题:AcWing 872. 最大公约数​​​​​​​

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值