ガウス過程回帰を使おうとして、最初に必ずぶつかる壁があります。「どのカーネルを選べばいいのか」という問題です。RBFカーネルを選べば滑らかな関数が得られますが、周期性は表現できません。周期カーネルを選べば周期は表せますが、周期の長さを事前に知っている必要があります。Matérnカーネルなら粗さを調整できますが、やはり手で選ぶしかありません。データに合うカーネルを試行錯誤で当てる――これでは、せっかくのノンパラメトリックな柔軟性が台無しです。
ここで発想を一段ひっくり返してみます。「カーネルそのものを設計する」のではなく、「カーネルのスペクトル(周波数の中身)をデータから学習する」のです。音を聞いて「低い音と高い音が混ざっている」とわかるように、信号の周波数成分さえ捉えられれば、滑らかさも周期性も自動的に表現できるはずです。この考えを正面から形にしたのが、Wilson と Adams が 2013 年の ICML で提案した スペクトル混合カーネル(Spectral Mixture kernel, SMカーネル) です。
SMカーネルは2つの強力な性質を持ちます。第一に、混合数を増やせば 任意の定常カーネルを任意の精度で近似できる(万能近似)。第二に、学習したスペクトルから信号に潜む周期を自動的に発見し、学習範囲の外まで構造を保ったまま外挿(extrapolation)できる。この性質は、たとえば大気中のCO2濃度予測(上昇トレンド+年周期を未来へ延長)や、テクスチャ画像の補完、時系列の長期予測などで威力を発揮します。
本記事の内容
- 定常カーネルとスペクトル密度を結ぶ ボホナーの定理 の直感と意味
- RBFカーネル・周期カーネルのスペクトルが何を表しているか
- スペクトルをガウス混合でモデル化し、逆フーリエ変換でSMカーネルを導出する全過程
- なぜSMカーネルが外挿でき、周期を自動発見できるのか
- ハイパーパラメータの意味と、経験スペクトルからの初期化
- PythonによるSMカーネルの実装、GP事後計算、RBFとの外挿比較
前提知識
この記事を読む前に、以下の記事を読んでおくと理解が深まります。
- ガウス過程回帰を初めから分かりやすく解説
- カーネル関数の種類と性質 — ガウス過程で使うカーネルを徹底解説
- ガウス過程からランダムに関数をサンプリングする
- ガウス過程のハイパーパラメータ最適化 — 周辺尤度最大化を解説
カーネル選択の難しさ — なぜスペクトルを考えるのか
ガウス過程回帰では、関数の事前分布をカーネル(共分散関数)$k(x, x’)$ で指定します。カーネルは「入力 $x$ と $x’$ がどれくらい似ているか=関数値が連動するか」を決める、いわば関数の性格そのものです。問題は、この性格を人間が決め打ちしなければならないことでした。
たとえば代表的なカーネルを並べてみましょう。RBF(ガウス)カーネルは無限回微分可能な滑らかな関数を生みますが、距離が離れれば相関は急速にゼロへ落ちます。つまり「遠くのことは何もわからない」ので、データのない領域では事前平均(ふつうは0)に戻ってしまいます。周期カーネルは周期構造を表せますが、周期 $p$ をハイパーパラメータとして与える必要があり、しかも「ぴったり1つの周期」しか表現できません。現実のデータは、上昇トレンド・年周期・週周期・ノイズがすべて混ざっているのに、です。
ここで音の世界を思い出してください。複雑な楽器の音色も、フーリエ解析にかければ「どの周波数がどれだけ含まれるか」というスペクトルに分解できます。基音と倍音の混ざり具合が音色を決めるのです。同じように、ガウス過程が生む関数も「どんな周波数成分が含まれるか」で性格が決まるとしたら――カーネルを直接いじる代わりに、スペクトルを設計(あるいは学習)すればよいことになります。
この「カーネル ↔ スペクトル」の橋渡しを厳密に保証するのが、次に見るボホナーの定理です。

上の図は、これから主役になる対応関係を示しています。左が時間(入力差)領域のカーネル $k(\tau)$、右が周波数領域のスペクトル密度 $S(s)$ です。両者はフーリエ変換でぴったり結ばれています。RBFカーネルの場合、時間領域のガウス山が、周波数領域でもガウス山に対応します。次節で、この対応がなぜ常に成り立つのかを定理として述べます。
ボホナーの定理 — 定常カーネルとスペクトル密度の双対
定常カーネルとは
まず舞台を整理します。カーネル $k(x, x’)$ が 定常(stationary) であるとは、入力の差 $\tau = x – x’$ だけに依存することをいいます。
$$ k(x, x’) = k(\tau), \quad \tau = x – x’ $$
RBF、Matérn、周期カーネルはみな定常です。「位置そのもの」ではなく「どれだけ離れているか」だけで相関が決まる、という自然な仮定です。この定常性こそが、フーリエ解析と相性がよい鍵になります。
ボホナーの定理
定常カーネルについて、19世紀末〜20世紀初頭に確立された次の美しい定理があります。
ボホナーの定理(Bochner’s theorem): 連続な関数 $k(\tau)$ が(正規化された)定常カーネル(=正定値関数)であるための必要十分条件は、$k(\tau)$ がある非負の有限測度のフーリエ変換として書けることである。密度 $S(s)$ を持つ場合、
$$ \begin{equation} k(\tau) = \int_{-\infty}^{\infty} S(s)\, e^{2\pi i s \tau}\, ds \end{equation} $$
ここで $S(s) \geq 0$ を スペクトル密度(spectral density) と呼びます。逆向きに、スペクトル密度はカーネルのフーリエ変換で得られます。
$$ S(s) = \int_{-\infty}^{\infty} k(\tau)\, e^{-2\pi i s \tau}\, d\tau $$
この定理が言っているのは、「定常カーネルであること」と「スペクトル密度が非負であること」は完全に等価だ、ということです。言い換えれば、$S(s) \geq 0$ を満たす関数を1つ用意して逆フーリエ変換すれば、それは自動的に正しいカーネル(正定値性を満たす共分散関数)になります。
なぜ「非負」が効くのか
ここが直感の核心です。ふつう新しいカーネルを作ろうとすると、「正定値性」という厄介な条件をチェックしなければなりません。どんな点の集合に対しても共分散行列が半正定値になる、という条件です。これを時間領域で直接確かめるのは難しい。
ところがボホナーの定理は、その難問を周波数領域の単純な不等式 $S(s) \geq 0$ に翻訳してくれます。スペクトルが至るところ非負でありさえすれば、逆フーリエ変換した $k(\tau)$ は文句なしに正定値カーネルになる――この保証があるからこそ、私たちは安心して「スペクトルを自由に設計する」ことができるのです。
実数値カーネル(虚部がゼロ)に限ると、$k(\tau)$ が偶関数 $k(-\tau)=k(\tau)$ であることから $S(s)$ も偶関数 $S(-s)=S(s)$ になり、上の積分は余弦変換の形にまとまります。
$$ k(\tau) = \int_{-\infty}^{\infty} S(s)\cos(2\pi s\tau)\, ds = 2\int_{0}^{\infty} S(s)\cos(2\pi s\tau)\, ds $$
この余弦の形は後でSMカーネルの導出に直接効いてきます。
ここまでで「カーネルを設計する=スペクトルを設計する」という土台が固まりました。では、私たちがよく使うRBFや周期カーネルは、スペクトルの世界ではどんな顔をしているのでしょうか。
おなじみのカーネルをスペクトルで眺める
RBFカーネルのスペクトル
RBF(ガウス)カーネルは $$ k_{\mathrm{RBF}}(\tau) = \exp\!\left(-\frac{\tau^2}{2\ell^2}\right) $$ でした($\ell$ は長さスケール)。これをフーリエ変換します。ガウス関数のフーリエ変換はガウス関数になる、という有名な事実を使うと、
$$ S_{\mathrm{RBF}}(s) = \int_{-\infty}^{\infty} \exp\!\left(-\frac{\tau^2}{2\ell^2}\right) e^{-2\pi i s\tau}\, d\tau = \sqrt{2\pi}\,\ell\, \exp\!\left(-2\pi^2 \ell^2 s^2\right) $$
が得られます。これは原点 $s=0$ を中心とするガウス山です。

左がRBFカーネル、右がそのスペクトル密度です。長さスケール $\ell$ を大きくすると、時間領域のカーネルは広がる(相関が遠くまで届く)一方、スペクトルは原点付近にきゅっと集中します。これは「低周波(ゆっくりした変動)だけを許す」ことを意味します。重要なのは、スペクトルの山が常に原点 $s=0$ にある点です。原点から離れた周波数(=周期的な振動)には重みがゼロですから、RBFカーネルは周期成分を一切表現できません。データのない領域で平均に戻ってしまうのは、まさにこのためです。
周期カーネルのスペクトル
一方、周期カーネル $$ k_{\mathrm{per}}(\tau) = \exp\!\left(-\frac{2\sin^2(\pi\tau/p)}{\ell^2}\right) $$ はどうでしょう。$\sin$ が入っているので $k(\tau)$ 自体が周期 $p$ で振動します。そのスペクトルを計算すると、連続的な山ではなく、基本周波数 $1/p$ とその整数倍(高調波)に集中した離散的な線スペクトルになります。

右図の通り、周期カーネルのスペクトルは $s = 0, 1/p, 2/p, \dots$ という飛び飛びの周波数にだけ重みを持ちます。これは「周期 $p$ がぴったり1つに固定されている」ことの裏返しです。柔軟性はありません。
ここで自然な発想が芽生えます。RBFは「原点の1つの山」、周期カーネルは「飛び飛びの線」。ならば、スペクトルを「原点に縛られない、自由な位置の山の集まり」にすれば、両者を包含し、もっと多彩なカーネルを作れるのではないか? これがスペクトル混合カーネルのアイデアそのものです。
スペクトル混合カーネルの導出
スペクトルをガウス混合でモデル化する
SMカーネルの出発点は、ひとことで言えば 「スペクトル密度 $S(s)$ をガウス分布の混合でモデル化する」 ことです。混合分布なら、山をいくつでも、好きな位置・好きな幅で置けます。スペクトルが偶関数でなければならない(実数値カーネルの条件)ので、各成分は $+\mu_q$ と $-\mu_q$ に対称な一対のガウスとして置きます。
$$ \begin{equation} S(s) = \sum_{q=1}^{Q} \frac{w_q}{2}\Big[\, \mathcal{N}(s \mid \mu_q, v_q) + \mathcal{N}(s \mid -\mu_q, v_q)\,\Big] \end{equation} $$
各成分($q = 1, \dots, Q$)のパラメータの意味は次の通りです。
- $w_q \geq 0$: 成分 $q$ の 重み(その周波数帯がどれだけ寄与するか=信号分散への配分)
- $\mu_q \geq 0$: 成分 $q$ の 中心周波数(その周波数の逆数が「周期」になる)
- $v_q > 0$: 成分 $q$ の 分散(バンド幅。小さいほど鋭い=はっきりした周期、大きいほど広帯域=滑らかな成分)
ここで $\mathcal{N}(s\mid \mu, v) = \frac{1}{\sqrt{2\pi v}}\exp\!\big(-\frac{(s-\mu)^2}{2v}\big)$ は平均 $\mu$・分散 $v$ の1次元ガウスです。すべての成分が非負なので、$S(s)\geq 0$ は自動的に満たされます。つまりボホナーの定理により、これを逆フーリエ変換したものは確実に正しいカーネルになります。

上の図は、3つのガウス成分(破線)を足し合わせて1つのスペクトル密度 $S(s)$(赤)を作る様子です(見やすさのため $s \geq 0$ 側だけを描いています)。山の位置・高さ・幅を自由に選べるので、原点の山(RBF相当)も、離れた位置の鋭い山(周期成分)も、同じ枠組みで表せます。次に、このスペクトルを逆変換して時間領域のカーネルを取り出します。
逆フーリエ変換で時間領域へ
目標は、式(2)のスペクトルをボホナーの定理の式(1)に代入し、$k(\tau)$ の閉じた形を求めることです。まず1成分だけ取り出して、その逆フーリエ変換を計算します。鍵になるのは、「ガウスのフーリエ変換はガウス」 と 「周波数のシフトは時間領域での変調(余弦の掛け算)になる」 という2つの事実です。
中心 $\mu_q$ のガウス1個 $\mathcal{N}(s\mid \mu_q, v_q)$ の逆フーリエ変換を考えます。まず原点中心のガウス $\mathcal{N}(s\mid 0, v_q)$ の逆フーリエ変換は、
$$ \int_{-\infty}^{\infty} \frac{1}{\sqrt{2\pi v_q}} e^{-s^2/(2v_q)}\, e^{2\pi i s\tau}\, ds = \exp\!\left(-2\pi^2 v_q \tau^2\right) $$
という、時間領域のガウス(減衰関数)になります。ここで周波数シフト定理を使います。スペクトルを $+\mu_q$ だけずらすと、時間領域では $e^{2\pi i \mu_q \tau}$ が掛かります。
$$ \mathcal{N}(s\mid \mu_q, v_q) \;\xrightarrow{\text{逆FT}}\; e^{2\pi i \mu_q \tau}\,\exp\!\left(-2\pi^2 v_q \tau^2\right) $$
同様に $-\mu_q$ にずらした成分は $e^{-2\pi i \mu_q \tau}$ が掛かります。式(2)の1成分は $+\mu_q$ と $-\mu_q$ のガウスの平均ですから、この2つを足して2で割ります。
$$ \frac{1}{2}\Big(e^{2\pi i \mu_q \tau} + e^{-2\pi i \mu_q \tau}\Big)\exp\!\left(-2\pi^2 v_q \tau^2\right) $$
ここでオイラーの公式 $\cos\theta = \frac{1}{2}(e^{i\theta}+e^{-i\theta})$ を使うと、複素指数の和が余弦にまとまります。
$$ \cos(2\pi \mu_q \tau)\,\exp\!\left(-2\pi^2 v_q \tau^2\right) $$
虚部がきれいに消え、実数値の関数になりました。これに重み $w_q$ を掛けて全成分について和を取ると、SMカーネルの最終形が得られます。
$$ \begin{equation} \boxed{\; k_{\mathrm{SM}}(\tau) = \sum_{q=1}^{Q} w_q\, \exp\!\left(-2\pi^2 \tau^2 v_q\right)\cos\left(2\pi \tau \mu_q\right) \;} \end{equation} $$
これが Wilson & Adams (2013) のスペクトル混合カーネルです。形を読み解くと、各成分は 「ガウス減衰 $\exp(-2\pi^2\tau^2 v_q)$ で包まれた余弦 $\cos(2\pi\tau\mu_q)$」 になっています。つまり1成分が「振動しながら減衰する波」を表し、その重ね合わせがカーネル全体です。

上の図がまさにこの構造を示しています。2つの成分(破線)はそれぞれ周波数 $\mu_q$ で振動し、$v_q$ で決まる速さで減衰します。それらの和(青)がSMカーネルです。$\mu_q$ が「周期 $1/\mu_q$」を、$v_q$ が「その周期がどれだけ遠くまで効くか(コヒーレンス長)」を、$w_q$ が「その成分の強さ」を支配しているのが見て取れます。
RBFと周期カーネルを特別な場合として含む
導出した式(3)が、おなじみのカーネルをきちんと特別な場合として含むことを確認しましょう。まず $\mu_q = 0$ とすると $\cos(0)=1$ なので、
$$ k(\tau) = w_q \exp(-2\pi^2 v_q \tau^2) $$
となり、これは RBFカーネルそのものです($2\pi^2 v_q = 1/(2\ell^2)$ と読み替えれば一致)。一方、$v_q \to 0$(バンド幅をゼロに)とすると減衰項が消え、
$$ k(\tau) = w_q \cos(2\pi \mu_q \tau) $$
という純粋な余弦カーネル(周期 $1/\mu_q$)になります。つまりSMカーネルは、$\mu_q$ と $v_q$ を選ぶだけでRBFから純周期まで連続的に行き来できる、極めて広いカーネル族なのです。混合数 $Q$ を増やせば、ボホナーの定理に基づき任意の定常カーネルを任意精度で近似できることも示されています(ガウス混合が任意の連続密度を近似できることの帰結)。
ここまでで、SMカーネルが「スペクトルを自由に積む」ことで生まれた万能なカーネルだとわかりました。次に、この性質が実際の回帰でどう効くのか――特に外挿の場面を見ていきます。
なぜSMカーネルは外挿でき、周期を発見できるのか
外挿のメカニズム
ガウス過程の事後平均は、訓練点でのカーネル値の重み付き和です。RBFカーネルでは $k(\tau)\to 0$($\tau$ が大きいとき)なので、訓練点から遠く離れた点の予測は「どの訓練点とも相関がない=情報がない」状態になり、事前平均(0)へ滑らかに戻ります。これがRBFが外挿できない数学的な理由です。
SMカーネルは違います。式(3)の各成分は $\cos(2\pi\mu_q\tau)$ という周期項を持つため、$\tau$ が大きくなっても(減衰が緩やかなら)相関が振動しながら残ります。「100単位先の点は、ちょうど1周期分(あるいは整数周期分)離れた過去の点と強く相関する」と判断できるのです。だからこそ、学習範囲の外でも周期構造を保ったまま予測を伸ばせます。

左がRBF、右がSMカーネルによる外挿です(赤い点線が訓練範囲の境界)。RBFは境界を越えた途端に事後平均が0へ平坦化し、不確実性(影)が急速に広がります。一方SMカーネルは、学習した周期成分を境界の外まで延長し、真の関数(破線)の振動をかなり正しく追従しています。不確実性も、周期構造を反映して振動的に増えていきます。これがSMカーネルの最大の実用的価値です。
周期の自動発見
SMカーネルのもう1つの魅力は、データから周期を自動で見つける点です。混合成分の中心周波数 $\mu_q$ がそのまま「データに含まれる周波数」に対応するので、学習後に $\mu_q$ を見れば「このデータには周期 $1/\mu_1$、$1/\mu_2$、… が含まれる」と読み取れます。人間が周期を指定する必要はありません。

左の信号は周期5($s=0.2$)と周期2($s=0.5$)が混ざったものです。右図で、データの経験スペクトル(灰色=周期グラム)の2つの山の位置に、学習されたガウス混合の中心 $\mu_q$(赤)がぴたりと乗っているのがわかります。SMカーネルは、この2つの周波数を成分として取り込むことで、信号に潜む周期を定量的に同定しています。
では、この $w_q, \mu_q, v_q$ という多数のパラメータは、どうやって決めるのでしょうか。次節でハイパーパラメータ最適化を扱います。
ハイパーパラメータの最適化と初期化
周辺尤度の最大化
SMカーネルのハイパーパラメータは、各成分の $\{w_q, \mu_q, v_q\}_{q=1}^Q$ とノイズ分散 $\sigma_n^2$ です。$Q$ 成分なら $3Q+1$ 個。これらを、ガウス過程の標準的な方法である 対数周辺尤度(log marginal likelihood)の最大化 で決めます。観測を $\boldsymbol{y}$、訓練入力で作ったカーネル行列を $\boldsymbol{K}_\theta$(ノイズ込みで $\boldsymbol{K}_\theta + \sigma_n^2\boldsymbol{I}$)とすると、
$$ \log p(\boldsymbol{y}\mid\theta) = -\frac{1}{2}\boldsymbol{y}^\top \boldsymbol{K}_\theta^{-1}\boldsymbol{y} – \frac{1}{2}\log|\boldsymbol{K}_\theta| – \frac{n}{2}\log 2\pi $$
を $\theta = \{w_q, \mu_q, v_q, \sigma_n^2\}$ について最大化します。第1項がデータへの当てはまり、第2項がモデルの複雑さへの罰則(オッカムの剃刀)として働き、両者のバランスで最適なスペクトルが選ばれます。詳しい導出と勾配計算は ガウス過程のハイパーパラメータ最適化 を参照してください。
初期化が成否を分ける
SMカーネルの周辺尤度は多峰(多数の局所最適)で、初期値が悪いと貧弱な局所解にはまります。直感的には当然で、「間違った周波数に成分を置いた」状態から勾配を登っても、なかなか正しい周波数へは移れません。Wilson & Adams が推奨する実践的な初期化は、データの経験スペクトル(周期グラムやFFTパワー)から成分を初期化することです。
具体的には、(1) データの経験スペクトル密度を計算し、(2) そのピーク位置を中心周波数 $\mu_q$ の初期値に、(3) ピークの高さを重み $w_q$ に、(4) ピークの幅を分散 $v_q$ に割り当てます。こうすれば「だいたい正しい周波数」からスタートでき、最適化が安定します。混合数 $Q$ は、表現したい周期成分の数に応じて選びます(多すぎると過学習・計算量増、少なすぎると表現力不足)。

上の図は、複雑な目標スペクトル(破線)を $Q=1, 2, 3$ の混合で近似する様子です。$Q=1$ では1つの山しか作れず大きくずれますが、$Q$ を増やすにつれて目標の3つの山を捉え、近似精度が上がっていきます。これがSMカーネルの万能近似性の実演です。実用上は $Q$ を増やしすぎると局所最適と計算コストが問題になるため、経験スペクトルのピーク数を目安に選ぶのが定石です。
理論はここまでです。実際にSMカーネルを実装し、事前サンプル・回帰・外挿を確かめてみましょう。
Pythonでの実装
SMカーネルの実装
まず式(3)をそのまま関数にします。スカラ入力(1次元時系列)を想定し、入力差 $\tau$ に対するカーネル値を返します。
import numpy as np
def sm_kernel(tau, w, mu, v):
"""スペクトル混合カーネル k(tau) = Σ w_q exp(-2π²τ²v_q) cos(2πτμ_q)
w: 重み配列, mu: 中心周波数配列, v: 分散配列 (いずれも長さ Q)"""
tau = np.asarray(tau)
k = np.zeros_like(tau, dtype=float)
for wq, mq, vq in zip(w, mu, v):
k += wq * np.exp(-2 * np.pi**2 * tau**2 * vq) * np.cos(2 * np.pi * tau * mq)
return k
def gram(X1, X2, kfun):
"""入力ベクトルからカーネル行列(グラム行列)を作る"""
T = X1[:, None] - X2[None, :] # 全ペアの差 τ = x - x'
return kfun(T)
ポイントは gram 関数です。SMカーネルは定常なので、全入力ペアの差 $\tau = x – x’$ を作り、それに sm_kernel を適用するだけでカーネル行列が完成します。各成分は「減衰ガウス × 余弦」の積で、足し合わせるだけなので実装は素直です。
スペクトル密度との対応を確認
導出が正しいか、「スペクトル混合 → 逆フーリエ変換 → SMカーネル」が数値的に一致するかを確かめます。式(2)のスペクトルを数値積分(式(1)の逆変換)してカーネルを作り、解析形の式(3)と比べます。
import numpy as np
def sm_spectral_density(s, w, mu, v):
"""スペクトル密度 S(s) = Σ (w_q/2)[N(s;μ_q,v_q)+N(s;-μ_q,v_q)]"""
s = np.asarray(s)
S = np.zeros_like(s, dtype=float)
for wq, mq, vq in zip(w, mu, v):
g1 = np.exp(-(s - mq)**2 / (2*vq)) / np.sqrt(2*np.pi*vq)
g2 = np.exp(-(s + mq)**2 / (2*vq)) / np.sqrt(2*np.pi*vq)
S += 0.5 * wq * (g1 + g2)
return S
w, mu, v = [0.6, 0.4], [0.3, 1.2], [0.01, 0.04]
# 解析形のカーネル
tau = np.linspace(0, 6, 7)
k_analytic = sm_kernel(tau, w, mu, v)
# スペクトルを数値的に逆フーリエ変換して作ったカーネル
s = np.linspace(-6, 6, 20001) # 十分広い周波数範囲
S = sm_spectral_density(s, w, mu, v)
k_numeric = np.array([np.trapezoid(S * np.cos(2*np.pi*s*t), s) for t in tau])
for t, ka, kn in zip(tau, k_analytic, k_numeric):
print(f"τ={t:.1f} 解析={ka:+.5f} 数値積分={kn:+.5f} 誤差={abs(ka-kn):.2e}")
このコードを実行すると、各 $\tau$ で解析形(式3)と数値積分(式1にスペクトルを代入)が小数5桁以上で一致します(誤差は $10^{-5}$ 程度以下で、数値積分の離散化誤差の水準)。これは、ガウス混合スペクトルの逆フーリエ変換が確かに「減衰余弦の和」になる、という導出が正しいことの数値的な裏付けです。実部のみで虚部が消えることも、cos だけで再現できていることから確認できます。
SM-GPからの事前サンプルと事後回帰
次に、SMカーネルを使ったガウス過程から関数をサンプリングし、観測データに対する事後分布(回帰)を計算します。
import numpy as np
rng = np.random.default_rng(3)
w, mu, v = [0.7, 0.3], [0.15, 0.8], [0.002, 0.01]
kf = lambda T: sm_kernel(T, w, mu, v)
# 事前サンプル: K = L L^T のコレスキー分解で生成
X = np.linspace(0, 12, 250)
K = gram(X, X, kf) + 1e-8 * np.eye(len(X))
L = np.linalg.cholesky(K)
prior_samples = [L @ rng.standard_normal(len(X)) for _ in range(4)]
# 事後(回帰): 真の関数 + ノイズの観測から事後平均・分散を計算
f_true = lambda x: np.sin(2*np.pi*0.15*x) + 0.5*np.sin(2*np.pi*0.8*x)
Xtr = np.sort(rng.uniform(0, 7, 25)) # 0〜7だけで学習
noise = 0.05
ytr = f_true(Xtr) + noise * rng.standard_normal(len(Xtr))
Xte = np.linspace(0, 12, 300) # 7より先は外挿
Ktr = gram(Xtr, Xtr, kf) + noise**2 * np.eye(len(Xtr))
Ks = gram(Xte, Xtr, kf)
Kss = gram(Xte, Xte, kf)
Kinv = np.linalg.inv(Ktr)
post_mean = Ks @ Kinv @ ytr # 事後平均
post_cov = Kss - Ks @ Kinv @ Ks.T # 事後共分散
post_sd = np.sqrt(np.clip(np.diag(post_cov), 0, None))
print(f"外挿域(x>7)の予測標準偏差の平均: {post_sd[Xte>7].mean():.3f}")
上のコードは事前サンプルと事後(回帰)の両方を計算しています。事前サンプルは「準周期的でうねりのある関数」になり、SMカーネルが周期構造を内包していることがわかります。事後では、$x \in [0,7]$ だけで学習したにもかかわらず、$x>7$ の外挿域でも周期構造を保った予測平均が得られ、不確実性は周期を反映して振動的に増えていきます。これらを可視化したのが次の図です。

左の事前サンプルは、複数の周波数が混ざった準周期的な関数です。RBFのようなのっぺりした滑らかさではなく、明確なうねりを持っているのがSMカーネルの特徴です。右の事後回帰では、訓練範囲(赤点線の左)でデータに密着し、外挿域(右)でも真の関数(破線)の周期構造を追えています。$\pm 2\sigma$ の帯が外挿域で広がるものの、平均に潰れず振動を保っている点が、RBFとの決定的な違いです。
RBFカーネルとの外挿比較
最後に、同じデータに対してRBFカーネルとSMカーネルの外挿性能を直接比べます。SMカーネルの優位がはっきり見えます。
import numpy as np
rng = np.random.default_rng(5)
f_true = lambda x: np.sin(2*np.pi*0.2*x) + 0.4*np.cos(2*np.pi*0.5*x)
Xtr = np.linspace(0, 8, 40)
noise = 0.05
ytr = f_true(Xtr) + noise * rng.standard_normal(len(Xtr))
Xte = np.linspace(0, 16, 400) # 8より先が外挿域
# RBFカーネル
ell = 1.0
rbf = lambda T: np.exp(-T**2 / (2*ell**2))
# SMカーネル(信号の周波数0.2と0.5に成分を配置)
w, mu, v = [0.6, 0.4], [0.2, 0.5], [8e-4, 8e-4]
smf = lambda T: sm_kernel(T, w, mu, v)
def gp_predict(kf):
Ktr = gram(Xtr, Xtr, kf) + noise**2 * np.eye(len(Xtr))
Ks = gram(Xte, Xtr, kf)
Kinv = np.linalg.inv(Ktr)
return Ks @ Kinv @ ytr
mean_rbf = gp_predict(rbf)
mean_sm = gp_predict(smf)
# 外挿域での真値との二乗平均平方根誤差(RMSE)
mask = Xte > 8
rmse = lambda m: np.sqrt(np.mean((m[mask] - f_true(Xte[mask]))**2))
print(f"外挿域RMSE RBF={rmse(mean_rbf):.3f} SM={rmse(mean_sm):.3f}")
このコードを実行すると、外挿域でのRMSEはSMカーネルの方が大幅に小さくなります(RBFは真値の振幅が約1なのに対し誤差が0.7前後=ほぼ予測できていない一方、SMはその半分以下に収まります)。RBFの事後平均は訓練範囲の境界を越えるとすぐ0へ戻るため、振動する真の関数とは全く合いません。対してSMカーネルは、学習した周波数成分を外挿域まで延長し、真の関数の周期を正しく追従します。理論で論じた「余弦項が遠方の相関を保つ」という性質が、数値でもはっきり確認できました。
応用
SMカーネルの「周期の自動発見+外挿」は、構造を持つ時系列・空間データの予測で広く役立ちます。代表的な応用を挙げます。
- 時系列の長期予測: トレンドと複数の季節成分(年・週・日など)が混ざるデータを、1つのカーネルでまとめて学習し、未来へ外挿できます。
- 大気CO2濃度予測: 上昇トレンドと年周期を同時にモデル化する古典的なベンチマーク。Wilson & Adams の論文でもSMカーネルの外挿性能が示されています。
- テクスチャ・画像補完: 2次元に拡張したSMカーネルで、規則的な模様(テクスチャ)の欠損部を周期構造から補完できます。
- 音声・音響モデリング: 信号の倍音構造(基音と高調波)がそのままスペクトル成分に対応するため、自然に表現できます。
下の図は、合成したCO2風データ(上昇トレンド+年周期)に対する外挿の例です。

訓練データ(黒)の8年分から、トレンド(線形成分)と年周期(SMカーネルでモデル化した残差)を学習し、将来(赤点線の右)へ延長しています。SM-GPの予測(青)は、将来の真値(赤点)の上昇傾向と季節的な揺れの両方を捉えています。トレンドと周期を別々に手で組まなくても、スペクトルを学習する枠組みが自動で構造を見つけてくれるのがSMカーネルの強みです。
まとめ
本記事では、ガウス過程のスペクトル混合カーネルを、ボホナーの定理という理論的土台から導出し、その外挿能力と周期発見の仕組みを解説しました。
- ボホナーの定理: 定常カーネルとスペクトル密度はフーリエ変換対 $k(\tau)=\int S(s)e^{2\pi i s\tau}ds$ で結ばれ、$S(s)\geq 0$ がカーネルの正定値性と等価になる。だからスペクトルを自由に設計できる。
- おなじみのカーネルのスペクトル: RBFは原点中心のガウス(周期表現不可)、周期カーネルは離散的な線スペクトル(周期1つに固定)。
- SMカーネルの導出: スペクトルをガウス混合 $S(s)=\sum_q \frac{w_q}{2}[\mathcal{N}(s\mid\mu_q,v_q)+\mathcal{N}(s\mid-\mu_q,v_q)]$ とし、逆フーリエ変換すると $k_{\mathrm{SM}}(\tau)=\sum_q w_q \exp(-2\pi^2\tau^2 v_q)\cos(2\pi\tau\mu_q)$ という「減衰余弦の和」が得られる。
- 万能近似と特別ケース: $\mu_q=0$ でRBF、$v_q\to0$ で純周期カーネルに帰着し、$Q$ を増やせば任意の定常カーネルを近似できる。
- 外挿と周期発見: 余弦項が遠方の相関を保つため学習範囲外へ外挿でき、中心周波数 $\mu_q$ がデータの周期を自動同定する。
- 最適化と初期化: $3Q+1$ 個のハイパーパラメータを対数周辺尤度最大化で学習する。周辺尤度は多峰なので、経験スペクトルのピークから $\{w_q,\mu_q,v_q\}$ を初期化するのが成功の鍵。
数値実験では、SMカーネルがRBFよりはるかに正確に外挿し、混合成分の中心がデータの周期にぴたりと一致することを確認しました。カーネルを手で選ぶ時代から、スペクトルを学習する時代へ――SMカーネルはその転換点を示す、理論的にも実用的にも美しいアイデアです。
次のステップとして、以下の記事も参考にしてください。