フーリエ級数は関数を三角関数の和で表す強力なツールですが、「元の関数のエネルギーはフーリエ係数にどう配分されるか?」という疑問に答えるのがパーセバルの等式(Parseval’s equality)です。この等式は、時間領域でのエネルギーと周波数領域でのエネルギーが等しいことを保証する、信号処理・物理学における基本的な定理です。
パーセバルの等式は、フーリエ解析の理論的な基盤であるだけでなく、通信工学やスペクトル解析での信号電力の計算にも直結します。
本記事の内容
- パーセバルの等式の定義
- 三角フーリエ級数からの導出
- 複素フーリエ級数での表現
- エネルギースペクトルの物理的意味
- Pythonでの数値検証
前提知識
この記事を読む前に、以下の記事を読んでおくと理解が深まります。
パーセバルの等式とは
パーセバルの等式は、関数の $L^2$ ノルム(二乗積分の平均)がフーリエ係数の二乗和に等しいことを述べる定理です。大雑把に言うと、「信号のエネルギーは、時間領域で計算しても周波数領域で計算しても同じ」ということです。
三角フーリエ級数でのパーセバルの等式
準備:フーリエ級数の復習
周期 $T$、基本角周波数 $\omega_0 = 2\pi / T$ の関数 $f(t)$ のフーリエ級数展開は:
$$ f(t) = \frac{a_0}{2} + \sum_{n=1}^{\infty} \left( a_n \cos n\omega_0 t + b_n \sin n\omega_0 t \right) $$
フーリエ係数 $a_n$, $b_n$ は:
$$ a_n = \frac{2}{T} \int_0^T f(t) \cos n\omega_0 t \, dt, \quad b_n = \frac{2}{T} \int_0^T f(t) \sin n\omega_0 t \, dt $$
導出
パーセバルの等式を導出するために、$f(t)$ の二乗の1周期平均を計算します。
$$ \frac{1}{T} \int_0^T |f(t)|^2 \, dt $$
$f(t)$ のフーリエ級数展開を代入します:
$$ \frac{1}{T} \int_0^T \left[ \frac{a_0}{2} + \sum_{n=1}^{\infty} \left( a_n \cos n\omega_0 t + b_n \sin n\omega_0 t \right) \right]^2 dt $$
ここで、三角関数の直交性を使います。異なる周波数の三角関数の積の1周期積分はゼロになります:
$$ \frac{1}{T} \int_0^T \cos m\omega_0 t \cos n\omega_0 t \, dt = \begin{cases} \frac{1}{2} & (m = n \neq 0) \\ 0 & (m \neq n) \end{cases} $$
$$ \frac{1}{T} \int_0^T \sin m\omega_0 t \sin n\omega_0 t \, dt = \begin{cases} \frac{1}{2} & (m = n \neq 0) \\ 0 & (m \neq n) \end{cases} $$
$$ \frac{1}{T} \int_0^T \cos m\omega_0 t \sin n\omega_0 t \, dt = 0 \quad (\text{すべての } m, n) $$
直交性により、クロスタームはすべて消えます。残るのは同じ周波数どうしの積のみです:
$$ \frac{1}{T} \int_0^T |f(t)|^2 \, dt = \left(\frac{a_0}{2}\right)^2 + \sum_{n=1}^{\infty} \left( a_n^2 \cdot \frac{1}{2} + b_n^2 \cdot \frac{1}{2} \right) $$
整理すると、三角フーリエ級数に対するパーセバルの等式が得られます:
$$ \boxed{\frac{1}{T} \int_0^T |f(t)|^2 \, dt = \frac{a_0^2}{4} + \frac{1}{2} \sum_{n=1}^{\infty} \left( a_n^2 + b_n^2 \right)} $$
複素フーリエ級数でのパーセバルの等式
複素フーリエ係数を用いた表現
複素フーリエ級数 $f(t) = \sum_{n=-\infty}^{\infty} c_n e^{jn\omega_0 t}$ では、パーセバルの等式はより簡潔に書けます。
$f(t)$ の二乗平均を計算します:
$$ \frac{1}{T} \int_0^T |f(t)|^2 \, dt = \frac{1}{T} \int_0^T f(t) \overline{f(t)} \, dt $$
$f(t)$ と $\overline{f(t)}$ にフーリエ級数を代入します:
$$ = \frac{1}{T} \int_0^T \left( \sum_{n=-\infty}^{\infty} c_n e^{jn\omega_0 t} \right) \left( \sum_{m=-\infty}^{\infty} \overline{c_m} e^{-jm\omega_0 t} \right) dt $$
積分と和の順序を交換し、複素指数関数の直交性:
$$ \frac{1}{T} \int_0^T e^{j(n-m)\omega_0 t} \, dt = \delta_{nm} $$
を用いると、$n = m$ の項だけが残ります:
$$ = \sum_{n=-\infty}^{\infty} c_n \overline{c_n} = \sum_{n=-\infty}^{\infty} |c_n|^2 $$
したがって、複素フーリエ係数に対するパーセバルの等式は:
$$ \boxed{\frac{1}{T} \int_0^T |f(t)|^2 \, dt = \sum_{n=-\infty}^{\infty} |c_n|^2} $$
三角形式との整合性の確認
三角形式のフーリエ係数と複素形式のフーリエ係数の関係は以下のとおりです:
$$ c_0 = \frac{a_0}{2}, \quad c_n = \frac{a_n – jb_n}{2}, \quad c_{-n} = \frac{a_n + jb_n}{2} \quad (n \geq 1) $$
したがって:
$$ |c_n|^2 + |c_{-n}|^2 = \frac{a_n^2 + b_n^2}{4} + \frac{a_n^2 + b_n^2}{4} = \frac{a_n^2 + b_n^2}{2} $$
これを代入すると:
$$ \sum_{n=-\infty}^{\infty} |c_n|^2 = |c_0|^2 + \sum_{n=1}^{\infty} \left(|c_n|^2 + |c_{-n}|^2\right) = \frac{a_0^2}{4} + \frac{1}{2}\sum_{n=1}^{\infty}(a_n^2 + b_n^2) $$
三角形式のパーセバルの等式と一致することが確認できました。
エネルギースペクトルの物理的意味
パーセバルの等式の左辺 $\frac{1}{T}\int_0^T |f(t)|^2 dt$ は、信号 $f(t)$ の平均パワーです。たとえば $f(t)$ が電圧信号であれば、$1\,\Omega$ の抵抗で消費される平均電力に相当します。
右辺の各項 $|c_n|^2$ は、周波数 $n\omega_0$ の成分が持つパワー寄与です。つまり:
- 信号の総パワーは、各周波数成分のパワーの和に等しい
- 異なる周波数成分間にはエネルギーの干渉がない
- $|c_n|^2$ を $n$ の関数としてプロットしたものがパワースペクトル密度の離散版
この性質は、信号処理やスペクトル解析で非常に重要です。信号のエネルギーがどの周波数帯に集中しているかを定量的に評価できます。
Pythonでの数値検証
理論を数値的に検証します。矩形波とのこぎり波に対して、パーセバルの等式の左辺(時間領域での二乗平均)と右辺(フーリエ係数の二乗和)を比較します。
import numpy as np
import matplotlib.pyplot as plt
T = 2 * np.pi
omega0 = 2 * np.pi / T
t = np.linspace(0, T, 10000, endpoint=False)
# --- 矩形波 ---
def square_wave(t):
return np.where(np.mod(t, T) < T / 2, 1.0, -1.0)
# --- のこぎり波 ---
def sawtooth_wave(t):
return 2 * (np.mod(t, T) / T) - 1
fig, axes = plt.subplots(2, 2, figsize=(14, 10))
for idx, (wave_func, wave_name) in enumerate([
(square_wave, "Square wave"),
(sawtooth_wave, "Sawtooth wave")
]):
f_t = wave_func(t)
# 左辺:時間領域でのパワー
lhs = np.mean(f_t ** 2)
# 右辺:フーリエ係数の二乗和(項数を増やしながら)
N_values = np.arange(1, 201)
rhs_cumulative = []
a0 = (2 / T) * np.trapz(f_t, t)
running_sum = (a0 / 2) ** 2
for n in N_values:
an = (2 / T) * np.trapz(f_t * np.cos(n * omega0 * t), t)
bn = (2 / T) * np.trapz(f_t * np.sin(n * omega0 * t), t)
running_sum += 0.5 * (an ** 2 + bn ** 2)
rhs_cumulative.append(running_sum)
rhs_cumulative = np.array(rhs_cumulative)
# (1) エネルギー収束
axes[idx, 0].plot(N_values, rhs_cumulative, 'b-', lw=1.5, label='RHS (cumulative)')
axes[idx, 0].axhline(lhs, color='r', ls='--', lw=2, label=f'LHS = {lhs:.6f}')
axes[idx, 0].set_xlabel('Number of terms $N$')
axes[idx, 0].set_ylabel('Energy')
axes[idx, 0].set_title(f'Parseval convergence ({wave_name})')
axes[idx, 0].legend()
axes[idx, 0].grid(True, alpha=0.3)
# (2) パワースペクトル
cn_squared = []
for n in range(0, 51):
an = (2 / T) * np.trapz(f_t * np.cos(n * omega0 * t), t)
bn = (2 / T) * np.trapz(f_t * np.sin(n * omega0 * t), t)
if n == 0:
cn_squared.append((an / 2) ** 2)
else:
cn_squared.append(0.5 * (an ** 2 + bn ** 2))
cn_squared = np.array(cn_squared)
axes[idx, 1].stem(range(51), cn_squared, linefmt='b-', markerfmt='bo', basefmt='gray')
axes[idx, 1].set_xlabel('Harmonic number $n$')
axes[idx, 1].set_ylabel('$|c_n|^2$')
axes[idx, 1].set_title(f'Power spectrum ({wave_name})')
axes[idx, 1].grid(True, alpha=0.3)
# 検証結果を表示
error = abs(lhs - rhs_cumulative[-1])
print(f"{wave_name}: LHS = {lhs:.8f}, RHS (N=200) = {rhs_cumulative[-1]:.8f}, "
f"Error = {error:.2e}")
plt.tight_layout()
plt.show()
矩形波では奇数次高調波のみにエネルギーが分布し、のこぎり波ではすべての高調波にエネルギーが分布することが確認できます。どちらの場合も、項数 $N$ を増やすと右辺が左辺に収束し、パーセバルの等式が数値的に成り立つことが分かります。
まとめ
本記事では、パーセバルの等式について解説しました。
- 三角フーリエ級数: $\frac{1}{T}\int_0^T |f(t)|^2 dt = \frac{a_0^2}{4} + \frac{1}{2}\sum_{n=1}^{\infty}(a_n^2 + b_n^2)$
- 複素フーリエ級数: $\frac{1}{T}\int_0^T |f(t)|^2 dt = \sum_{n=-\infty}^{\infty} |c_n|^2$
- 物理的意味: 信号の平均パワーは各周波数成分のパワーの総和に等しい
- エネルギースペクトル: $|c_n|^2$ は各周波数成分のパワー寄与を表す
次のステップとして、以下の記事も参考にしてください。