因子和倍数问题
因子和倍数问题
简单记ϕ(x)表示x的因子数。
题目1:给定正整数g,找到g的所有素因子。其中1≤g≤1018。
首先考虑如何找到给定数g的所有素因子。这个用Pollard Rho算法就可以了,时间复杂度为O(g1/4(log2g)2),但是实际上跑的飞快。
题目2:给定正整数g,要求找到g的所有因子。其中1≤g≤1018。
先找到所有素因子,之后可以直接暴力递归搜它的所有因子。后者时间复杂度为O(ϕ(x))。注意这里ϕ(x)只有10万级别大小。
题目3:给定正整数g,以及数p,其中gcd(g,p)=1。要求找到最小的正整数x满足gx=1(modp)。其中1≤g,p≤109
由欧拉定理知gφ(p)=1(modp),利用辗转法不难得知x∣φ(p)。因此我们只需要从φ(p)开始递减即可,不断删除一些素因子,直到不能删为止。在计算出φ(p)后,接下来的时间复杂度为O((log2p)2)。
题目4:给定正整数g,考虑g的所有因子。接下来处理n个元素x1,…,xn,其中xi是g的因子。之后对所有g的因子d,计算x中有多少数是是d的因子。
可以发现整除关系可以构成一个非常庞大的有向图,很难搞。但是整除关系实际上原本有向图简单规则得多。
考虑唯一的素数分解g=pc11…pckk。我们可以用向量(c1,…,ck)来唯一表示g。这时候所有g的因子也可以如法表示。现在问题变成了一个高维数组前缀和。后者计算的时间复杂度为O(kϕ(g))。
题目5:给定正整数g。之后给定n个数x1,…,xn,要求计算∪ni=1{kxi(modg)∣k≥0}的大小。其中1≤g≤109,1≤n≤105
实际上xi的意义是将所有gcd(xi,g)的倍数全部标记。而问题要求我们计算有多少数最终被标记。接下来我们可以认为xi=gcd(xi,g)。
首先对数据进行去重。如果我们直接维护bitset暴力计算的话,时间复杂度为O(∑d∣gd),它的值约为O(glnlng)。不是很大。
还有一种更加高效的方式是发现ϕ(g)≤1200。我们可以根据容斥计算。记录dp(i,j)表示仅考虑x1,…,xi,被选中的元素的最小公倍数为j,总共的方案数(带符号,选择奇数次为正号,偶数次为负号)。其对外的贡献只有两种,因此可以O(ϕ(g)2log2g)计算。
最终的结果为∑d∣gdp(n,d)×gd−n。
素数
素数是指大于1,且除了1和自身外,没有其它因子的整数。
π(x)表示所有小于等于x的正整数中素数的数目,在x足够大的时候,π(x)≈xlnx。
素数筛
素数筛用于查找所有小于等于n的所有素数。下面给出一些筛法以及对应的时间复杂度:
- 暴力判断每个数是否是素数,时间复杂度为O(n√n)。
- 欧拉筛,时间复杂度为O(n)。
- 暴力枚举所有数的倍数,并标记它们为合数,时间复杂度为O(nlnn)。
- 埃拉托斯特尼筛法,暴力枚举所有素数的倍数,并标记它们为合数。时间复杂度为O(nlnlnn)。
统计因子和倍数的方式
考虑这样一个问题,给定一个数组a1,…,an,每个数都大于等于1,且不超过M。且1≤n,M≤107。
记f(x)=∑ni=1[ai|x],即序列a中有多少数是x的因子。
要求输出f(1),…,f(M)。
首先我们记c(x)表示x在a序列中出现的次数。之后考虑如何解决这个问题。
这个问题有很多做法,最简单的是枚举所有的因子,这样可以给出O(M√M)的时间复杂度。
还有一种做法,就是我们仅考虑每个数的所有倍数,并进行统计。这样时间复杂度为O(MlnM)的时间复杂度。
还有一种做法,就是我们考虑所有素数的倍数,并进行统计。这样时间复杂度为O(MlnlnM)。
这里我们仅详细讲一下最后一种方式,这种方式我是从这个评论学到的。代码如下:
let primes be all prime of [1, M];
f = g;
for(p in primes) {
for(i = 1; i * p <= M; i++){
f[i * p] += f[i];
}
}
记pi表示第i小的素数,很显然时间复杂度为∑π(M)i=1Mpi,根据素数定理,π(M)≈MlnM,因此pπ(M)≈M,可以得出px≈xlnx。代入进去可以得到:
π(M)∑i=1Mpi≈Mπ(M)∑i=21ilni≈M∫π(M)i=21xlnxdx≈M[lnlnx]π(M)2≈MlnlnM因此可以得出时间复杂度为O(MlnlnM)。
现在我们考虑算法的具体含义。记fi表示处理完第i个素数后f数组的取值。这时候有f0=c,f1(x)=∑kf0(xpk1)。
f2(x)=∑kf1(xpk2)=∑k∑jf0(xpk2pj1)换言之ft(x)表示x枚举所有i1,…,it,c(x∏tj=1pijj)的和。而fπ(M)(x)自然就是所有x的因子和。
我们提到的这个问题是统计因子的,但是统计倍数也可以用类似的做法优化到O(MlnlnM)。