フーリエ級数は、周期関数を三角関数(正弦波・余弦波)の無限和で表す手法であり、信号処理、音響学、熱伝導、振動解析など、科学技術のあらゆる分野で使われています。「あらゆる周期関数は正弦波の重ね合わせで表せる」というフーリエの大胆な主張は、解析学の発展に革命をもたらしました。
本記事の内容
- フーリエ級数の定義
- 三角関数の直交性
- フーリエ係数の導出
- 矩形波のフーリエ展開
- Pythonでの部分和の可視化
フーリエ級数の定義
周期 $2L$ の関数 $f(x)$ のフーリエ級数は次で定義されます。
$$ \boxed{f(x) = \frac{a_0}{2} + \sum_{n=1}^{\infty}\left[a_n \cos\frac{n\pi x}{L} + b_n \sin\frac{n\pi x}{L}\right]} $$
フーリエ係数 $a_n$, $b_n$ は:
$$ a_n = \frac{1}{L}\int_{-L}^{L} f(x)\cos\frac{n\pi x}{L} \, dx \quad (n = 0, 1, 2, \dots) $$
$$ b_n = \frac{1}{L}\int_{-L}^{L} f(x)\sin\frac{n\pi x}{L} \, dx \quad (n = 1, 2, 3, \dots) $$
三角関数の直交性
フーリエ係数の公式は、三角関数系が区間 $[-L, L]$ 上で直交関数系をなすことから導かれます。
$$ \int_{-L}^{L} \cos\frac{m\pi x}{L}\cos\frac{n\pi x}{L} \, dx = \begin{cases} 0 & (m \neq n) \\ L & (m = n \neq 0) \\ 2L & (m = n = 0) \end{cases} $$
$$ \int_{-L}^{L} \sin\frac{m\pi x}{L}\sin\frac{n\pi x}{L} \, dx = \begin{cases} 0 & (m \neq n) \\ L & (m = n) \end{cases} $$
$$ \int_{-L}^{L} \cos\frac{m\pi x}{L}\sin\frac{n\pi x}{L} \, dx = 0 \quad (\text{全ての } m, n) $$
フーリエ係数の導出
$a_n$ を求めるために、フーリエ級数の両辺に $\cos(n\pi x/L)$ を掛けて $[-L, L]$ で積分します。
$$ \int_{-L}^{L} f(x)\cos\frac{n\pi x}{L} \, dx = \frac{a_0}{2}\underbrace{\int_{-L}^{L}\cos\frac{n\pi x}{L}dx}_{=0 \,(n\neq 0)} + \sum_{k=1}^{\infty} a_k \underbrace{\int_{-L}^{L}\cos\frac{k\pi x}{L}\cos\frac{n\pi x}{L}dx}_{=L\delta_{kn}} $$
直交性により $k = n$ の項のみ残り、$a_n \cdot L$ が得られます。
$$ \therefore \quad a_n = \frac{1}{L}\int_{-L}^{L} f(x)\cos\frac{n\pi x}{L} \, dx $$
$b_n$ も同様に $\sin(n\pi x/L)$ を掛けて導出します。
具体例: 矩形波
周期 $2\pi$ の矩形波:
$$ f(x) = \begin{cases} 1 & (0 < x < \pi) \\ -1 & (-\pi < x < 0) \end{cases} $$
$f(x)$ は奇関数なので $a_n = 0$(全ての $n$)。$b_n$ を計算すると、
$$ \begin{align} b_n &= \frac{1}{\pi}\int_{-\pi}^{\pi} f(x)\sin(nx) \, dx = \frac{2}{\pi}\int_0^{\pi}\sin(nx)\,dx \\ &= \frac{2}{n\pi}[-\cos(nx)]_0^{\pi} = \frac{2}{n\pi}(1-\cos(n\pi)) \\ &= \begin{cases} \frac{4}{n\pi} & (n \text{ が奇数}) \\ 0 & (n \text{ が偶数}) \end{cases} \end{align} $$
$$ f(x) = \frac{4}{\pi}\sum_{k=0}^{\infty}\frac{\sin((2k+1)x)}{2k+1} = \frac{4}{\pi}\left(\sin x + \frac{\sin 3x}{3} + \frac{\sin 5x}{5} + \cdots\right) $$
Pythonでの実装
import numpy as np
import matplotlib.pyplot as plt
x = np.linspace(-np.pi, 3*np.pi, 1000)
# 矩形波の原関数
def square_wave(x):
return np.sign(np.sin(x))
# フーリエ部分和
def fourier_partial_sum(x, N):
result = np.zeros_like(x)
for k in range(N):
n = 2*k + 1
result += np.sin(n * x) / n
return result * 4 / np.pi
fig, axes = plt.subplots(1, 2, figsize=(14, 5))
# 部分和の収束
y_exact = square_wave(x)
for N in [1, 3, 5, 10, 50]:
y_approx = fourier_partial_sum(x, N)
axes[0].plot(x, y_approx, label=f'N={N}', alpha=0.7)
axes[0].plot(x, y_exact, 'k--', linewidth=2, label='矩形波', alpha=0.5)
axes[0].set_title('矩形波のフーリエ級数(部分和の収束)')
axes[0].set_xlabel('x')
axes[0].set_ylabel('f(x)')
axes[0].legend()
axes[0].grid(True, alpha=0.3)
axes[0].set_ylim(-1.5, 1.5)
# 各周波数成分
n_terms = 5
for k in range(n_terms):
n = 2*k + 1
component = (4/(n*np.pi)) * np.sin(n * x)
axes[1].plot(x, component + 2*k, label=f'n={n}')
axes[1].axhline(y=2*k, color='gray', linewidth=0.3)
axes[1].set_title('各周波数成分(オフセット表示)')
axes[1].set_xlabel('x')
axes[1].set_ylabel('振幅(オフセット)')
axes[1].legend()
axes[1].grid(True, alpha=0.3)
plt.tight_layout()
plt.savefig('fourier_series.png', dpi=150, bbox_inches='tight')
plt.show()
部分和の項数 $N$ を増やすと矩形波に近づきますが、不連続点付近では約9%のオーバーシュート(ギブズ現象)が残ることが確認できます。
まとめ
- フーリエ級数: 周期関数を三角関数の無限和で表す
- フーリエ係数は三角関数の直交性から導出される
- 偶関数は余弦級数のみ、奇関数は正弦級数のみ
- 不連続点でのギブズ現象(約9%のオーバーシュート)
次のステップとして、以下の記事も参考にしてください。