ACM_素数筛法 唯一分解定理 欧拉函数(附容斥)

本文详细介绍了素数筛法的原理、证明和优化方法,包括从2开始筛选,优化为从i * i开始,以及考虑不超过sqrt(n)的素因子。接着讲解了唯一分解定理,通过素数表分解数字,并展示了应用实例。最后,阐述了欧拉函数的概念,给出了其计算公式,并利用容斥原理进行证明。
摘要由CSDN通过智能技术生成

引言

本文将介绍素数筛法:
主要从他的原理, 证明, 代码, 优化来介绍
随后介绍和它有关的唯一分解定理, 以及相似的欧拉函数

素数筛法:

一个同辗转相除法同样古老的算法
原理: 如果x 是素数 那么2x, 3x, 4x……都不是素数, 所以如果我们从2开始往后筛, 筛到n, 这时候n没有被前面的任何数标记成不是素数, 那么n就是素数
证明:
第一点: 如果x 是素数 那么2x, 3x, 4x……都不是素数 这个很简单不多说
第二点: 所以如果我们从2开始往后筛, 筛到n, 这时候n没有被前面的任何数标记成不是素数, 那么n就是素数
反证法: 如果n 不是 素数, 那么必然存在a, b (a是素数) 使得 a*b = n, 而我们的数字是从小到大的, 所以在我们运行到a的时候必定会标记2a, 3a, 4a ……不是素数(这里边一定存在a * b), 表示n被其他数标记成了不是素数, 这与没有标记明显矛盾, 所以n一定是素数;

所以筛选素数的时候我们可以这样(这不是最终形态):

#include <cstdio>
#include <cstring>

const int N = 1000000 + 10;

bool isprime[N];
int prime[N];

void makeprime(int n) {
    memset(isprime, 1, sizeof isprime);
    isprime[1] = 0;
    for(int i = 2; i < n; ++i) {
        if(isprime[i]) for(int j = i+i; j < n; j += i)
            isprime[j] = 0;
    }
}

int getprime(int n) {
    int k = 0;
    for(int i = 1; i < n; ++i) {
        if(isprime[i]) prime[k++] = i;
    }
    return k;
}

int main() {
    makeprime(N);
    int prime_size = getprime(N);
    
  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值