唯一分解定理
任何大于1的自然数,都可以唯一分解成有限个质数的乘积.
n = p 1 α 1 p 2 α 2 . . . p k α k ( p i 均为质数 , 指数 α k 为正整数 ) n = p_1^{\alpha_1}p_2^{\alpha_2}...p_k^{\alpha_k}(p_i均为质数,指数\alpha_k为正整数) n=p1α1p2α2...pkαk(pi均为质数,指数αk为正整数)
欧拉函数
表示小于等于 n 且和 n 互质的数的个数 表示小于等于n且和n互质的数的个数 表示小于等于n且和n互质的数的个数
ϕ ( 1 ) = 1 \phi(1) = 1 ϕ(1)=1
1. 当 n 是质数时 , ϕ ( n ) = n − 1 1.当n是质数时,\phi(n) = n - 1 1.当n是质数时,ϕ(n)=n−1
2. g c d ( a , b ) = 1 , ϕ ( a × b ) = ϕ ( a ) × ϕ ( b ) 2.gcd(a,b)=1,\phi(a \times b) = \phi(a) \times \phi(b) 2.gcd(a,b)=1,ϕ(a×b)=ϕ(a)×ϕ(b)
3. 若 n = p k , 其中 p 是质数 , 那么 ϕ ( n ) = p k − p k − 1 3.若n = p^k,其中p是质数,那么 \phi(n) = p^k - p^{k - 1} 3.若n=pk,其中p是质数,那么ϕ(n)=pk−pk−1
4. 由唯一分解定理 , 设 n = ∏ i = 1 s p i k i , 其中 p i 是质数 , 有 ϕ ( n ) = n × ∏ i = 1 s p i − 1 p i 4.由唯一分解定理,设 n = \prod_{i = 1}^{s}p_i^{k_i}, 其中p_i是质数,有 \phi(n) = n \times \prod_{i = 1}^s\frac{p_i - 1}{p_i} 4.由唯一分解定理,设n=∏i=1spiki,其中pi是质数,有ϕ(n)=n×∏i=1spipi−1
裴蜀定理
设 a , b 是不全为零的整数 , 则存在整数 x , y , 使得 a x + b y = g c d ( a , b ) 设a,b是不全为零的整数,则存在整数x,y,使得ax + by = gcd(a,b) 设a,b是不全为零的整数,则存在整数x,y,使得ax+by=gcd(a,b)
如果 a , b 互质 ( 即 g c d ( a , b ) = 1 ) , 那么一定存在两个整数 x 与 y , 使得 a x + b y = 1 如果a,b互质(即gcd(a,b) = 1),那么一定存在两个整数x与y,使得 ax + by = 1 如果a,b互质(即gcd(a,b)=1),那么一定存在两个整数x与y,使得ax+by=1
费马小定理
若 p 为素数 , g c d ( a , p ) = 1 , 则 a p − 1 ≡ 1 ( m o d p ) 若p为素数,gcd(a,p) = 1,则a^{p - 1} \equiv 1 (\mod p) 若p为素数,gcd(a,p)=1,则ap−1≡1(modp)
对于任意整数 a , 有 a p ≡ a ( m o d p ) 对于任意整数a, 有a^{p} \equiv a(\mod p) 对于任意整数a,有ap≡a(modp)
欧拉定理
若 g c d ( a , m ) = 1 , 则 a ϕ ( m ) ≡ 1 ( m o d m ) 若gcd(a,m) = 1,则 a^{\phi(m)} \equiv 1(\mod m) 若gcd(a,m)=1,则aϕ(m)≡1(modm)
乘法逆元
typedef long long int ll;
const int maxn = 3e6 + 7;
ll n, p, inv[maxn];
ll qpow(ll a,ll b,ll m){
b %= m;
ll ret = 1,x = a;
while (b){
if (b & 1)ret = (ret * x) % m;
x = (x * x) % m;
b >>= 1;
}
return ret;
}
//(a,a mod b) ==> (b,a - kb) ==> (b,a - b a/b)
//ax + by = bx' + (a - kb) * y'
//ax + by = bx' + ay' - a/b b y'
//a(x - y') + b(y - (x - a/b * y')) = 0
ll exgcd(ll a, ll b, ll &x, ll &y){
if (a < b) return exgcd(b, a, y, x);
if (b == 0){
x = 1;
y = 0;
return a;
}
else{
ll x1;
ll d = exgcd(b, a % b, x1, x);
y = x1 - a / b * x;
return d;
}
}
int main()
{
cin >> n >> p;
inv[1] = 1;
ll x, y;
for (int i = 2; i <= n; i++){
//p = k * i + r;
//k * i + r =- 0 mod p
//kr_1 + r_1=- 0 mod p
//i_1 = -p/i * (p mod i)_1 mod p
inv[i] = (p - p / i)* inv[p % i] % p; //递推
//inv[i] = qpow(i, p - 2, p); //快速幂
//exgcd(i, p, x, y); //扩展欧几里得
//inv[i] = (x % p + p) % p;
}
for (int i = 1; i <= n; i++)printf("%d\n", inv[i]);
return 0;
}
快速GCD
int binary_zc(int a){
int c = a & -a,ans = 0;
while (c >>= 1)ans++;
return ans;
}
int gcd(int a, int b)
{
int az = __builtin_ctz(a), bz = __builtin_ctz(b);
int z = min(az, bz);
int dif;
b >>= bz;
while (a)
{
a >>= az;
dif = b - a;
az = __builtin_ctz(dif);
if (a<b) b = a;
if (dif<0) a = -dif;
else a = dif;
}
return b << z;
}