欧拉函数

欧拉函数

欧拉函数是一类非常重要的数论函数

建议阅读 数论函数基础 章节,了解基本概念与先要知识


此处获取本节调试数据 / 代码包

全文 绝大多数 内容是对 [0] 中讲述的 粗略抄写胡乱加工


1. 定义与性质

定义

\([1, n]\) 中与 \(n\) 互质的数的个数,记作 \(\varphi (n)\)

形式化的说,\(\varphi (n) = \sum _ {i = 1} ^ n [i \perp n]\)


性质

  1. 显然,当 \(n \in \mathbb P\) 时,有 \(\varphi (n) = n - 1\)

    质数和 小于它的所有数 互质

  2. \([1, p ^ k]\) 中所有非 \(p\) 整倍数的数均与 \(p ^ k\) 互质,故有 \(\varphi (p ^ k) = (p - 1) p ^ {k - 1}\)

    证明显然

  3. \(\varphi\)积性函数,即若 \(a \perp b\),则 \(\varphi (ab) = \varphi (a) \varphi (b)\)

    数论函数基础 - 常见函数,分类及证明 中给出了 两种思路的详细证明

  4. 计算式 \(\varphi (n) = \prod \varphi (p ^ {c}) = \prod {p ^ c \times \dfrac {p - 1} p} = n \prod {\dfrac {p - 1} p}\)

    根据前两条性质,以及 唯一分解 容易证明

  5. \(a \mid b\),则 \(\varphi (ab) = a \times \varphi (b)\)

    由于 \(a \mid b\),故 \(b\)质因数 包含 \(a\)质因数

    换言之,\(b\)本质不同质因数集 等于 \(ab\)本质不同质因数集

    故根据计算式 \(\varphi (ab) = ab \prod \dfrac {p - 1} p = a (b \prod \dfrac {p - 1} p) = a \times \varphi (b)\)

    同理可以证明 \(a \mid b\) 时有 \(\varphi (a) \mid \varphi (b)\)\(\prod\) 部分可以整除)

  6. \(n > 2\),则 \(2 \mid \varphi (n)\)

    考虑 计算式\(p ^ c \times \dfrac {p - 1} p\) 当且仅当 \(p = 2, c = 1\) 时为 奇数,然后容易证明

  7. 使得 \(\gcd (n, x) = d, x \in [1, n]\)\(x\) 个数为 \(\varphi \left ( \dfrac n d \right)\)

    \(a = \dfrac n d, b = \dfrac x d\),于是有 \(a \perp b\),然后就 根据定义显然

  8. \(\sum _ {d \mid n} \varphi (d) = n\),也被称为 欧拉反演

    这里给出一种不同于 [0] 中的证明思路

    我们考虑使用 莫比乌斯反演,即 \(f (n) = \sum _ {d \mid n} g (d) \Longleftrightarrow g (n) = \sum _{d \mid n} \mu (d) f \left ( \dfrac n d \right)\)

    我们代入 \(f (n) = n, g (n) = \varphi (n)\),于是我们尝试证明 \(\varphi (n) = \sum _ {d \mid n} \mu (d) \times \dfrac n d\)

    考虑 \(\mu\) 的特性,当且仅当 \(d = \prod p\)\(p\) 互不相同 且是 \(n\)质因子)时,才会有贡献

    而当 \(d\)偶数个质因子 时,\(\mu (d)\),反之 \(\mu (d)\) 贡献为

    这与计算式 \(\varphi (n) = n \prod \dfrac {p - 1} p = n \prod \left (1 - \dfrac 1 p \right)\)容斥系数 相符合

    容易知道它们相等

    不够直观的话我们来举个例子,设有 \(n = p_1 ^ 2 \times p_2 ^ 3 \times p_3\)

    根据 计算式

    \[\begin {aligned} \varphi (n) &= n \prod \left ( 1 - \dfrac 1 p \right) \\ &= n \left ( 1 - \dfrac 1 {p_1} \right) \left ( 1 - \dfrac 1 {p_2} \right) \left ( 1 - \dfrac 1 {p_3} \right) \end {aligned} \]

    而使得 \(\mu (d) \neq 0\)\(d\) 显然只有 \(1, p_1, p_2, p_3, p_1p_2, p_2p_3, p_1p_3, p_1p_2p_3\) 这几种取值

    对应有式子

    \[\begin {aligned} \varphi (n) = 1 - (\dfrac n {p_1} + \dfrac n {p_2} + \dfrac n {p_3}) + (\dfrac n {p_1p_2} + \dfrac n {p_2p_3} + \dfrac n {p_1p_3}) - \dfrac n {p_1p_2p_3} \end {aligned} \]

    显然上下相等


2. 线性筛欧拉函数

根据 计算式,我们有一个 简易 的实现,我们知道

\[\begin {aligned} \varphi (n) = \begin {cases} p \times \varphi \left ( \dfrac n p \right ) & p ^ 2 \mid n \\ (p - 1) \times \varphi \left ( \dfrac n p \right ) & p ^ 2 \nmid n \end {cases} \end {aligned} \]

其实就是每个 质因数 只计算一次贡献,可以写出代码如下

inline void Sieve () {
	phi[1] = 1;
	for (uint32_t i = 2; i <= N; ++ i) {
		if (!Vis[i]) pri[++ Cnt] = i, phi[i] = i - 1;
		for (uint32_t k = 1; k <= Cnt && pri[k] * i <= N; ++ k) {
			Vis[i * pri[k]] = 1;
			if (i % pri[k] == 0) {
				phi[i * pri[k]] = phi[i] * pri[k];
				break ;
			}
			else phi[i * pri[k]] = phi[i] * (pri[k] - 1);
		}
	}
}

我们注意到 \(\varphi (p ^ k) = p \times \varphi (p ^ {k - 1}) ~ (k > 1)\),而 \(\varphi (p) = p - 1\),故 \(\varphi (p ^ k) = \varphi (p ^ {k - 1}) p\)


3. 欧拉定理

其实就是 费马小定理\(\operatorname {ex}\),可以拓展到部分 非素数的模数 情况

\[\begin {aligned} n ^ {\varphi (m)} \equiv 1 \pmod m && n \perp m \end {aligned} \]

我们发现,\(\{kn \bmod m\ | k \perp m, k \in [0, m) \} = \{k, | k \perp m, k \in [0, m)\}\)

也就是说当 \(k, n \perp m\) 时,\(kn \bmod m\) 的余数就是 \(m\) 互质的数的某种排列

证明与前面 费马小定理 相似,显然两个集合元素个数均为 \(\varphi (m)\) 个,只需证明 元素不重

考虑反证,相同时必然不符合 互质条件,故易得

于是我们把这 \(\varphi (m)\) 数相乘,显然其在 \(\bmod m\) 意义下成立,即有

\[(\prod kn) \bmod m \equiv \prod (kn \bmod m) \pmod m \]

故容易有 \(n ^ {\varphi (m)} \prod (kn \bmod m) \equiv \prod (kn \bmod m) \pmod m\)

可以知道 \(\prod (kn \bmod m) \perp m\),故两边可以同时 除掉这一部分,得到 \(n ^ {\varphi (m)} \equiv 1 \pmod m\)


4. 扩展欧拉定理

\[\begin {aligned} a ^ b \equiv \begin {cases} a ^ {b \bmod \varphi (m)} & \gcd (a, m) = 1 \\ a ^ b & \gcd (a, m) \neq 1, b < \varphi (m) & \pmod m \\ a ^ {(b \bmod \varphi (m)) + \varphi (m)} & \gcd (a, m) \neq 1, b \ge \varphi (m) \end {cases} \end {aligned} \]

证明似乎需要 巨大量分讨?今天脑子太糊了,鸽了

转一个 \(OI - Wiki\) 上的证明 [1]

形式证明
证明转载自 synapse7,并进行了一些整理。

  1. 命题: \(a\) 的从 0 次, 1 次到 \(b\) 次幂模 \(m\) 构成的序列中,存在 \(r\)\(s\) ,使得前 \(r\) 个数(即从 \(a^0 \bmod m\)\(\left.a^{r-1} \bmod m\right)\) 互不相同,从第 \(r\) 个数开始,每 \(s\) 个数就循环一次。

证明:

  • 由鸽巢定理易证。

我们把 \(r\) 称为 \(a\) 幂次模 \(m\) 的循环起始点, \(s\) 称为循环长度。(注意: \(r\) 可以为 0 )
用公式表述为: \(\forall i \geq r, a^i \equiv a^{i+s}(\bmod m)\)
2. 命题: \(a\) 为素数的情况,该式成立。

证明:

  • 若模 \(m\) 不能被 \(a\) 整除,而因为 \(a\) 是一个素数,那么 \(\operatorname{gcd}(a, m)=1\) 成立,根据欧拉定理,容易证明该式成立。
  • 若模 \(m\) 能被 \(a\) 整除,那么存在 \(r\)\(m^{\prime}\) 使得 \(m=a^r m^{\prime}\) ,且 \(\operatorname{gcd}\left(a, m^{\prime}\right)=1\) 成立。所以根据欧拉定理有 \(a^{\varphi\left(m^{\prime}\right)} \equiv 1\left(\bmod m^{\prime}\right)\)
    又由于 \(\operatorname{gcd}\left(a^r, m^{\prime}\right)=1\) ,所以根据欧拉函数的求值规则,容易得到:
    \(\varphi(m)=\varphi\left(m^{\prime}\right) \times(a-1) a^{r-1}\) ,即我们有: \(\varphi\left(m^{\prime}\right) \mid \varphi(m)\)
    所以 \(a^{\varphi\left(m^{\prime}\right)} \equiv 1\left(\bmod m^{\prime}\right), \varphi\left(m^{\prime}\right) \mid \varphi(m) \Longrightarrow a^{\varphi(m)} \equiv 1\left(\bmod m^{\prime}\right)\), 即 \(a^{\varphi(m)}=k m^{\prime}+1\)
    ,两边同时乘以 \(a^r\) ,得 \(a^{r+\varphi(m)}=k m+a^r\) (因为 \(m=a^r m^{\prime}\) )
    所以对于 \(m\) 中素因子 \(a\) 的次数 \(r\) 满足: \(a^r \equiv a^{r+\varphi(m)}(\bmod m)\) 。我们可以简单变换形式,得到 推论:

\[b>r \Longrightarrow a^b \equiv a^{r+((b-r) \bmod \varphi(m))} \quad(\bmod m) \]

又由于 \(m=a^r m^{\prime}\) ,所以 \(\varphi(m)=\varphi\left(a^r\right) \varphi\left(m^{\prime}\right) \geq \varphi\left(a^r\right)=a^{r-1}(a-1) \geq r\) (tips: \(a\) 是素数,最小是 2 ,而 \(r \geq 1\) )。
所以因为 \(\varphi(m) \geq r\) ,故有:

\[a^r \equiv a^{r+\varphi(m)} \equiv a^{r \bmod \varphi(m)+\varphi(m)} \quad(\bmod m) \]

所以

\[a^b \equiv a^{r+(b-r) \bmod \varphi(m)} 即 $a^b \equiv a^{b \bmod \varphi(m)+\varphi(m)}(\bmod m)$ 。 \]

  1. 命题: \(a\) 为素数的幂的情况,该式成立

证明:

  • 不妨令 \(a=p^k\) ,是否依然有 \(\forall r, a^r \equiv a^{r+\varphi(m)}(\bmod m)\) ?

答案是肯定的,由命题1 可知存在 \(s\) 使得 \(a^s \equiv 1(\bmod m)\) ,所以 \(p^{\operatorname{lcm}(s, k)} \equiv 1(\bmod m)\) ,所以令 \(s^{\prime}=\frac{s}{\operatorname{gcd}(s, k)}\) 时,我们能有 \(p^{s^{\prime} k} \equiv 1(\bmod m)\)
此时有关系: \(s^{\prime} \mid s\)\(s \mid \varphi(m)\) ,且 \(r^{\prime}=\left\lceil\frac{r}{k}\right\rceil \leq r \leq \varphi(m)\) ,由 \(r^{\prime}, s^{\prime}\)\(\varphi(m)\) 的关系,依然可以得到 \(a^b \equiv a^{b \bmod \varphi(m)+\varphi(m)}(\bmod m)\)
4. 命题: \(a\) 为合数的情况,该式成立。

证明:

  • 只证 \(a\) 拆成两个素数的幂的情况,大于两个的用数学归纳法可证。设 \(a=a_1 a_2\), 其中 \(a_i=p_i^{k_i}\) ,而 \(a_i\) 的循环长度为 \(s_i\)
    \(s \mid \operatorname{lcm}\left(s_1, s_2\right)\) ,由于 \(s_1\left|\varphi(m), s_2\right| \varphi(m)\) ,那么 \(\operatorname{lcm}\left(s_1, s_2\right) \mid \varphi(m)\) ,所以 \(s \mid \varphi(m)\)\(r=\max \left(\left\lceil\frac{r_i}{k_i}\right\rceil\right) \leq \max \left(r_i\right) \leq \varphi(m)\)
    \(r, s\)\(\varphi(m)\) 的关系,依然可以得到 \(a^b \equiv a^{b \bmod \varphi(m)+\varphi(m)}(\bmod m)\) 。证毕。

Luogu P5091 【模板】扩展欧拉定理

啊对,就是板子

#include <bits/stdc++.h>

uint32_t A, M, P, K;
bool BiggerthanM;
std::string B;

inline uint32_t phi (uint32_t x) {
	uint32_t Ret = x;
	for (uint32_t i = 2; i <= sqrt (x); ++ i)
		if (x % i == 0) {
			Ret = Ret / i * (i - 1);
			while (x % i == 0) x = x / i;
		}
	if (x > 1) Ret = Ret / x * (x - 1);
	return Ret;
}

inline uint32_t phi_mod_b () {
	uint32_t Ret = 0, Val = 0;
	for (uint32_t i = 0; i < B.size (); ++ i) {
		Ret = (Ret * 10 + (B[i] - '0')) % P, Val = Val * 10 + (B[i] - '0');
		if (Val > M) BiggerthanM = 1;
	}
	return Ret;
}

inline uint32_t qpow (uint32_t a, uint32_t b) {
	uint32_t Ret = 1;
	while (b) {
		if (b & 1) Ret = 1ull * a * Ret % M;
		a = 1ull * a * a % M, b >>= 1;
	}
	return Ret;
}

int main () {
	
	std::ios::sync_with_stdio(0);
	std::cin.tie(0), std::cout.tie(0);
	
	std::cin >> A >> M >> B;
	
	P = phi (M), K = phi_mod_b ();
	
	if (std::__gcd (A, M) == 1) std::cout << qpow (A, K) << '\n';
	else if (!BiggerthanM) std::cout << qpow (A, atoi (B.data ())) << '\n';
	else std::cout << qpow (A, K + P) << '\n';
	
	return 0;
}

Luogu P2158 [SDOI2008] 仪仗队

唐氏题,转化一下题意就是求 分母小于 \(N\)最简分数个数

容易想到 欧拉函数前缀和,然后随便做

尝试了一下用 \(Farey\) 序列来 暴力,优化的好可以过 \(35000\),非常牛

(甚至本地可以过 \(40000\)

#include <stdio.h>
#include <stdint.h>
#include <stdbool.h>

const int MAXN = 40005;

uint32_t pri[40005], phi[40005];
uint32_t Cnt = 0, Sum = 0, N;
bool Vis[40005];

void Sieve () {
	phi[1] = 1;
	for (uint32_t i = 2; i <= N; ++ i) {
		if (!Vis[i]) pri[++ Cnt] = i, phi[i] = i - 1;
		for (uint32_t j = 1; j <= Cnt && pri[j] * i <= N; ++ j) {
			Vis[i * pri[j]] = 1;
			if (i % pri[j] == 0) {
				phi[i * pri[j]] = pri[j] * phi[i];
				break ;
			}
			phi[i * pri[j]] = phi[i] * (pri[j] - 1);
		}
	}
}

int main () {
	
	scanf ("%u", &N);
	
	Sieve ();

	for (uint32_t i = 1; i < N; ++ i) Sum += phi[i];
	
	printf ("%u\n" ,(Sum << 1) + (N > 1));
	
	return 0;
}
#include <bits/stdc++.h>

struct Frac {
	uint32_t x, y;
	
	inline Frac operator + (const Frac &a) const {
		return {x + a.x, y + a.y};
	}
};

uint32_t N, Cnt;

inline void DFS (const Frac l, const Frac r) {
	Frac m = (l + r);
	if (m.x > N || m.x < m.y || m.y > N) [[unlikely]] return ;
	++ Cnt, DFS (l, m), DFS (m, r);
}

int main () {
	
	std::cin >> N, -- N;
	
//	if (N > 35000) return 1;
	
	DFS ({0, 1}, {1, 0});
	
	std::cout << (Cnt << 1) + (N > 0) << '\n';
	
	return 0;
}

5. 引用资料

[0] Number Theory —— H_W_Y

[1] 欧拉定理 & 费马小定理 —— OI Wiki

posted @ 2024-07-22 20:02  FAKUMARER  阅读(15)  评论(0编辑  收藏  举报