【积性函数基础学习】
积性函数基础学习
1. 什么是积性函数?
积性函数的两个定义:
(1) 积性函数:对于任意互质的整数a和b有性质f(ab)=f(a)f(b)的数论函数
(2) 完全积性函数:对于任意整数a和b有性质f(ab)=f(a)f(b)的数论函数。
观察以上对积性函数的定义,我们可以找出关于此类函数的特点:
(1) 在积性函数的定义f(ab)=f(a)*f(b)中,要求a和b都是整数。
(2) 对于普通的积性函数而言,存在额外的条件,要求a和b都互质(GCD(a,b)==1)。
(3) 所有积性函数满足f(ab)=f(a)*f(b)的运算规则。
2. 积性函数有什么性质?
性质一:
与算术基本定理有关。
3. 有哪些积性函数?
积性:
φ(n) -欧拉函数,计算与n互质的正整数之数目
μ(n) -莫比乌斯函数,关于非平方数的质因子数目
gcd(n,k)-最大公因子,当k固定的情况
d(n) -n的正因子数目
σ(n) -n的所有正因子之和
σk(n)-因子函数,n的所有正因子的k次幂之和,当中k可为任何复数。
1(n) -不变的函数,定义为 1(n) = 1 (完全积性)
Id(n)-单位函数,定义为 Id(n) = n(完全积性)
Idk(n)-幂函数,对于任何复数、实数k,定义为Idk(n) = n^k(完全积性)
ε(n) -定义为:若n = 1,ε(n)=1;若 n > 1,ε(n)=0。别称为“对于狄利克雷卷积的乘法单位”(完全积性)
λ(n) -刘维尔函数,关于能整除n的质因子的数目
γ(n),定义为γ(n)=(-1)^ω(n),在此加性函数ω(n)是不同能整除n的质数的数目
另外,所有狄利克雷特征均是完全积性的[1]
非积性:
冯·曼戈尔特函数:当n是质数p的整数幂,Λ(n)=ln(p),否则Λ(n)=0
不大于正整数n的质数的数目π(n)
整数拆分的数目P(n):一个整数能表示成正整数之和的方法的数目[2]
4. 积性函数实战!
例题1:[Hdu1452]Happy 2004
题意:
多组数据,每一次给你一个数X,定义函数F(A)为A的所有正因子之和,求F(2004^X)%29的值(1<=x<=10000000)。
分析:
X极大,2004^X更大,模的条件看上去帮不上太大的忙。鉴于这个函数的比较复杂的定义,让正因子相乘的做法又太过于暴力。
于是我们只能尝试挖掘这个函数本身的性质的方面下手了。
还记得我们曾在上面提到过的典型积性函数吗?其中有两个函数就可能在这里被我们用上。
σ(n) -n的所有正因子之和
σk(n)-因子函数,n的所有正因子的k次幂之和,当中k可为任何复数。
没错,我们所要求的F(2004^X)正是这里的σ(n),F(2004^X) --> FX(2004)正是这里的σk(n),他们都是积性函数。
我们将2004唯一分解化,2004 --> 2^2*3*167。根据上面所提到过的积性函数的性质,
f(abcd...)=f(a)*f(b)*f(c)*f(d)*...(a,b,c,d...之间两两互质)
也就是说,我们将FX(2004)变化成FX(2)*FX(2)*FX(3)*FX(167),而对于这几个函数,我们易知:
FX(2)=1+2^1+2^2+...+2^X=2^(X+1)-1 (正因子只有2)
FX(3)=1+3^1+3^2+...+3^X=(3^(3+1)-1)/2 (正因子只有3)
因为是在%29条件下进行的运算,FX(167)=FX(22)
FX(22)=1+22^1+22^2+...+22^X=(22^(X+1)-1)/21 (正因子只有167,现变为22,当然你也可以就带入167)
(P.S. 以上运算类似于等比数列求和公式:1+A^1+A^2...+A^X=(A^(X+1)-1)/A-1,只是因为他们的正因子仅为他们自己和1才会有这样的公式)
以上式子由于涉及模运算,除一个数就等于乘与它的乘法逆元(这个结论不会的同学可以搜索一下),好在29是素数,我们可以用费马小定理求出逆元,幂运算的操作用快速幂完成即可。
代码:
#include <map> #include <cmath> #include <ctime> #include <queue> #include <stack> #include <cstdio> #include <vector> #include <bitset> #include <cstring> #include <iostream> #include <algorithm> #define LL long long #define INF (0x3f3f3f3f) using namespace std; const int mod=29; int n; int QuickPow (int a,int k) { int cal=1; while(k>0) { if (k&1) cal=cal*a%mod; a=a*a%mod; k>>=1; } return cal; } int Inv (int a) { return QuickPow(a, mod-2); } int main () { while(cin >> n) { if (!n) break; int a=(QuickPow(2, 2*n+1)-1)%mod; int b=(QuickPow(3, n+1)-1)*Inv(2)%mod; int c=(QuickPow(22, n+1)-1)*Inv(21)%mod; int ans=a*b*c%mod; cout << ans << endl; } return 0; }
资料来源&推荐博客:
(1)百度百科:https://baike.baidu.com/item/%E7%A7%AF%E6%80%A7%E5%87%BD%E6%95%B0/8354949?fr=aladdin
(2)博客|浅谈一类积性函数的前缀和(已经全部是更后面的知识了,转载):http://blog.csdn.net/skywalkert/article/details/50500009
(3)博客|积性函数、线性筛、莫比乌斯反演和一堆乱七八糟的题目:http://jcvb.is-programmer.com/posts/41846.html