📜  车轮分解算法(1)

📅  最后修改于: 2023-12-03 15:28:14.944000             🧑  作者: Mango

车轮分解算法

车轮分解算法(Wheel Factorization Algorithm)是一种分解大质数的快速算法。该算法基于欧拉筛法和线性筛法,通过将待分解的数分为质数和非质数两类,分别采用不同的筛法,从而将时间复杂度优化至 $O(n^{\frac{1}{2}})$。

原理

假设待分解的数为 $n$,预处理得到一组素数 $primes$,其中最小的素数为 $p_1=2$。将 $n$ 和素数数组 $primes$ 中每个素数相除,直到商为 $1$。如果商等于素数数组中的某一个素数,则该素数一定是 $n$ 的一个因子。否则,$n$ 可以表示为素数的乘积。

为了加快算法的速度,我们需要预处理出某些不需要被测试的非质数,然后只测试剩下的数。这里我们采用欧拉筛法预处理了一组素数 $primes$,并提前处理了一些可以被素数整除的数。

实现
def wheel_factorization(n):
    # 预处理素数
    primes = [2, 3, 5, 7, 11, 13, 17, 19, 23, 29, 31, 37, 41, 43, 47, 53, 59, 61, 67, 71, 73, 79, 83, 89, 97]
    # 预处理被素数整除的数
    wheel = [1, 2, 2, 4, 2, 4, 2, 4, 6, 2, 6, 4, 2, 4, 6, 6]
    # 初始化
    i = 0
    factor = []
    # 轮询
    for p in primes:
        # 如果商等于素数,则该素数一定是 n 的一个因子
        while n % p == 0:
            factor.append(p)
            n //= p
        # 优化欧拉筛法和线性筛法的时间复杂度
        i += 1
        if i == len(wheel):
            i = 1
        p += wheel[i]
        # 如果 n 已经被分解完了,直接返回因子
        if n == 1:
            return factor
    # 如果 n 没有被分解完,说明 n 一定是一个质数
    factor.append(n)
    return factor
示例

调用 wheel_factorization(360) 即可得到 $360=2^3 \times 3^2 \times 5$ 的分解结果。