モジュール 5 ・ 目安 90 分

過学習との戦い — データ拡張と正則化

このモジュールで学ぶこと — 「よく学ぶ」と「学びすぎる」は違う

前のモジュールで、私たちはネットワークを自動で訓練するしくみ——損失を勾配降下で最小化する——を手に入れました。損失を下げれば下げるほど良いモデルになる、と素直に思いたくなります。ところが、ここに深層学習でもっとも重要で、もっとも厄介な落とし穴があります。訓練データでの損失を下げすぎると、かえって新しいデータに弱くなるのです。

これがモジュール1でも触れた 過学習(overfitting)(Overfitting) です。訓練データを丸暗記するように合わせ込んだ結果、まだ見ていないデータに対してうまく予測できなくなる。機械工学の実験にたとえるなら、測定点にぴったり通る高次の曲線を引いたら、測定ノイズまで忠実に再現してしまい、点と点の間ではとんでもない値を予測する——あの「過剰な曲線あてはめ」そのものです。

このモジュールの目標は、この過学習を見抜き、そして抑える技術を身につけることです。前半で「過学習をどう診断するか(学習曲線の読み方)」を学び、後半で「過学習をどう治療するか(データ拡張・Dropout・BatchNorm)」という具体的な武器を揃えます。そして最後に、前回のCIFAR-100ベースラインを、これらの武器で実際に改善する授業課題2の後半へとつなげます。前回が「動かす」だったのに対し、今回は「効かせる」回です。

汎化 — 本当に測りたいのは「見たことのないデータ」での性能

まず言葉を整理します。私たちがモデルに本当に期待しているのは、訓練で使ったデータを覚えることではなく、まだ見たことのないデータに対して正しく答えることです。この「未知のデータへの対応力」を 汎化(generalization)(Generalization) と呼びます。学習の真の目的は損失を下げることそのものではなく、汎化性能を高めることなのです。

ここでモジュール2で学んだ、データを訓練用(train)と検証用(validation)に分ける話が効いてきます。訓練データでの成績は、いわば「答えを見ながら解いた問題」の点数なので、丸暗記でも高くなってしまい、実力の指標になりません。そこで、学習には使わない 検証データ(validation set)(Validation Set) を別に取り分けておき、そちらでの成績を「実力」の代理として見ます。訓練での成績と検証での成績、この二つを並べて見ることが、過学習を診断する出発点になります。

過学習の反対側にある失敗も押さえておきましょう。モデルの容量が足りず、訓練データにすらうまく合わせられない状態を 未学習(underfitting)(Underfitting) と言います。過学習が「学びすぎ」なら、未学習は「学べていない」。私たちが探しているのは、その間にある「ちょうど良く学べた」状態です。

ここでモジュール1の「モデル容量」の話を思い出してください。容量が小さすぎるモデルは表現力が足りず未学習になり、大きすぎるモデルは訓練データを丸暗記できてしまうため過学習に傾きます。容量を横軸に検証性能を縦軸にとると、真ん中あたりで性能が最も高くなる山なりの関係が現れます。左に寄りすぎれば未学習、右に寄りすぎれば過学習——このバランスの舵取りこそが、深層学習の実務でずっと付き合っていくテーマです。そして重要なのは、容量を小さく抑える以外にも過学習を抑える手立てがある、という点です。この後で学ぶデータ拡張・Dropout・BatchNormは、まさに「容量は大きいまま、過学習だけを抑える」ための道具立てなのです。

学習曲線の読み方 — 二本の曲線の「乖離」を見る

過学習を目で見て診断する道具が 学習曲線(learning curve)(Learning Curve) です。横軸にエポック(学習の進み具合)、縦軸に損失(または精度)をとり、訓練データでの曲線と検証データでの曲線を同じグラフに二本描きます。この二本の関係を読むだけで、モデルの健康状態がかなり分かります。

典型的なパターンを頭に入れておきましょう。学習の序盤は、訓練損失も検証損失もそろって下がっていきます。これは順調に学べているサインです。ところがある時点から、訓練損失はさらに下がり続けるのに、検証損失は下げ止まり、やがて上昇に転じることがあります。この「二本の曲線が開いていく=乖離(かいり)」こそ、過学習が始まった決定的な合図です。モデルが訓練データの丸暗記に走り、未知データへの対応力を失いつつある、というわけです。

一方、二本ともまだ高い位置で横ばいなら、それは未学習——容量やエポックが足りていない兆候です。学習曲線を読めるようになると、「もっと学習を続けるべきか」「もう止めるべきか」「モデルを大きくすべきか小さくすべきか」の判断が、感覚ではなくデータに基づいてできるようになります。検証損失が上がり始める手前で学習を打ち切る**早期終了(early stopping)**も、この曲線を見ればこそ実行できる基本テクニックです。

可視化で試す — 学習曲線シミュレータ

下の学習曲線シミュレータで、いま説明した二本の曲線の乖離を自分で作り出してみましょう。まずデータ量のスライダーをうんと小さくしてください。データが少ないほどモデルは丸暗記しやすく、訓練曲線と検証曲線がくっきり開く——過学習が起きやすくなるのが見えるはずです。次にデータ量を増やしていくと、二本の曲線の隙間が縮まっていくのを確認してください。「データを増やすことが最強の過学習対策の一つ」という実感が得られます。

続いて、これから学ぶ武器を先取りで試せます。Dropout率を上げると乖離がどう変わるか、データ拡張をONにすると検証曲線がどう改善するか、そしてモデル容量を変えると未学習と過学習の間をどう行き来するか。スライダーを動かしながら、「二本の曲線を近づけて、しかも両方低くする」ちょうど良い設定を探してみてください。これが過学習との戦いの縮図です。

学習曲線シミュレータ

データ量を最小・容量を最大にして、train と val が大きく乖離(=過学習)する様子を見よう。/ そこから Dropout を上げ、データ拡張をONにして乖離が縮む代わりに収束が遅くなるのを確かめよう。
80件
7
0%
汎化ギャップ: 1.157大きい(過学習)
縦の破線は val 損失が最小になるエポック(早期終了の目安)。
0.000.250.500.751.001.25エポック →損失train(訓練)val(検証)

データ拡張 — 1枚の写真を、水増しして学ばせる

では、過学習を抑える具体的な武器を見ていきましょう。最初の、そしてもっとも効果的な武器が データ拡張(data augmentation)(Data Augmentation) です。発想は驚くほど素直で、「データが少ないなら、増やせばいい」。とはいえ新しい写真を撮ってくるのではなく、手元の画像に少し手を加えて、別のデータのように見せかけるのです。

たとえば猫の写真を1枚、左右反転させれば、それも立派な猫の写真です。少しだけ切り出して拡大したり(crop)、明るさや色合いを変えたり、画像の一部を四角く隠したり(RandomErase)——こうした変換を加えても「猫である」という正解は変わりません。ところがピクセルの値としては別物になるので、モデルにとっては新しい訓練例が増えたのと同じ効果があります。1枚の写真が、実質的に何十枚分ものバリエーションに化けるわけです。

なぜこれが過学習を抑えるのでしょうか。モデルが「たまたまこの画像のこの位置にこの模様がある」といった、本質と関係ない細部を丸暗記しようとしても、拡張のたびに画像が少しずつ変わるので暗記が通用しません。結果として、モデルは「反転しても切り取っても明るさが変わっても猫は猫」という、より本質的で頑健な特徴を学ばざるを得なくなります。これはちょうど、機械の検査アルゴリズムを、あえて照明条件や設置角度を変えた多様なサンプルで鍛えると、現場のばらつきに強くなるのと同じ理屈です。

可視化で試す — データ拡張プレビュー

下のデータ拡張プレビューで、一枚の画像に各変換をかけるとどう見えるかを確かめましょう。flip(反転)、crop(切り出し)、erase(一部消去)、明度変更のトグルを一つずつON/OFFして、元画像がどう変化するかを観察してください。同時に「この1枚が何枚分のバリエーションになるか」も表示されます。複数の変換を組み合わせると、水増しの効果が掛け算で効いていくことが見て取れるはずです。

ここで大事な感覚は、「正解が変わらない範囲で変換する」という節度です。数字の6を180度回転させたら9になってしまうように、やりすぎるとラベルが壊れて逆効果になります。どこまで変えてよいかは対象しだい——それを踏まえて、適度な拡張の組み合わせを探してみてください。

データ拡張プレビュー

反転と明度だけをONにして、同じ1枚から何通りの見た目が作れるか組合せ数を確かめよう。/ 消去(RandomErasing)もONにして、隠れても分類できるよう学ぶ狙いを想像してみよう。
1枚が何枚分に?
反転2 × 切り出し9 × 明度5 = 90 通り

Test Time Augmentation — 推論のときにも使う

データ拡張は訓練だけのものではありません。推論(予測)のときにも同じ発想が使えます。それが テスト時データ拡張(Test Time Augmentation, TTA)(Test Time Augmentation) です。一枚のテスト画像を判定するとき、その画像を反転したり少しずらしたりした複数のバージョンをすべてモデルに通し、出てきた予測を平均します。すると、たまたま一つの見え方で判断を誤っても、他のバージョンが補ってくれるので、判定がより安定します。少し計算は増えますが、後述するアンサンブルと同じ「多数決」の効果で精度を底上げできる、手軽なテクニックです。

アンサンブルからDropoutへ — 「弱いネットの多数決」

もう一つの強力な考え方が アンサンブル(ensemble)(Ensemble) です。これは「複数のモデルに予測させ、その多数決(平均)を取る」というやり方です。一人の専門家より、少しずつ得意分野の違う複数の専門家に相談して意見をまとめた方が、判断が安定して外れにくい——直感的にも納得できるでしょう。実際、それぞれ単体では平凡なモデルでも、寄せ集めて平均すると、単体を上回る性能が出ることがよくあります。

ただし、モデルを何個も別々に訓練するのは計算コストがかさみます。そこで「一つのネットワークの中で、擬似的にアンサンブルを実現できないか」という発想から生まれたのが ドロップアウト(Dropout)(Dropout) です。

Dropoutのしくみはシンプルです。訓練中、各更新のたびに、ネットワークのニューロンをランダムに一定割合(たとえば半分)だけ「お休み」させ、出力をゼロにします。休むニューロンは毎回変わります。すると、更新のたびに少しずつ違う「間引かれたネットワーク」で学習が進むことになります。これは実質的に、無数の少しずつ違うネットワークを同時に鍛えているのと同じで、推論時にはそれら全部を平均したような振る舞いになる——つまりアンサンブルの効果を一つのネットワークの中で疑似的に得ているわけです。

過学習を抑える効果もあります。特定のニューロンにいつでも頼れるわけではなくなるので、ネットワークは「一部の仲間が休んでも成り立つ、冗長で頑健な特徴」を学ぶようになります。一人のエースに依存したチームより、誰が抜けても回るチームの方が強い、という組織論にも通じる話です。休ませる割合(Dropout率)は効き具合を決めるつまみで、大きすぎると学習そのものが進まなくなるので、ほどほどが肝心です。

Batch Normalization — センサ信号を正規化してから学ぶ

最後の武器は バッチ正規化(Batch Normalization, BatchNorm)(Batch Normalization) です。これは過学習対策というより、学習を速く・安定して進めるための工夫ですが、結果的に汎化にも良い方向へ働くことが多く、現代のネットワークではほぼ標準装備になっています。

動機を機械工学の言葉で説明しましょう。複数のセンサから信号を集めて処理するとき、センサごとに単位もスケールもバラバラだと扱いにくい。だから前処理として、各信号を平均0・分散1くらいに揃える正規化をかけますね。ニューラルネットワークの中でも、同じ問題が起きています。層を通るうちにデータの分布がどんどんずれて広がったり偏ったりし、後ろの層は「毎回スケールの変わる入力」に振り回されて学習しにくくなるのです。

BatchNormがやることは、まさにこのセンサ信号の正規化です。各層に入ってくるデータを、ミニバッチ単位で平均0・分散1に揃えてから次へ流します。これで後ろの層は安定したスケールの入力を受け取れ、学習が速く進みます。

ただし、いつでも強制的に平均0・分散1にしてしまうと、ネットワークが本当は使いたかった分布の情報まで潰してしまうかもしれません。そこでBatchNormは、正規化したあとに**学習可能な二つのパラメータ γ\gamma(ガンマ)と β\beta(ベータ)**で、スケールと位置を調整し直します。

y=γx^+βy = \gamma\,\hat{x} + \beta

ここで x^\hat{x} が平均0・分散1に正規化された値です。γ\gamma で広げ直し、β\beta でずらし直す。つまり「いったんきれいに揃えてから、必要なら学習でちょうど良い分布に戻す」という二段構えです。無理に正規化を押しつけるのではなく、揃えるかどうかもネットワークに委ねている、というのが賢いところです。

可視化で試す — 分布正規化アニメーション

下のBatchNorm可視化で、この「揃えてから戻す」の流れを目で追いましょう。まず入力分布のずれ(平均や広がり)をスライダーで大きくしてみてください。偏った、扱いにくい分布ができます。それが正規化によって平均0・分散1のきれいなヒストグラムに揃う様子を確認します。次に γ\gammaβ\beta を動かすと、いったん揃えた分布が再びスケールされ、位置がずれていく——学習可能なパラメータが分布を「必要な形に戻している」ことが視覚的に分かるはずです。センサ信号の前処理と学習可能な微調整、その二段構えを体感してください。

BatchNorm 分布正規化アニメーション

「平均シフト」を動かして入力分布が偏るのを確認し、正規化後のヒストグラムが平均0に揃う様子を観察しよう。/ γとβを動かして、いったん揃えた分布が「必要な形に戻っていく」動きを確認しよう。

入力分布(センサ信号のイメージ)

2.5
2.00

学習可能パラメータ

1.5
0.5

μ=平均, σ=標準偏差
サンプル数: 300

① 入力 xずれた・ばらついた分布-808μ=2.45, σ=2.02
正規化
② 正規化後 x̂平均0・分散1に揃う-808μ=0.00, σ=1.00
γx̂+β
③ γ・β適用後 y学習で必要な分布に戻す-808μ=0.50, σ=1.50

入力が偏っていても、 正規化で平均0・分散1に揃え、 γ・βで必要な分布形に戻す——BatchNorm の二段構えです。

Colabで効かせる — 授業課題2を仕上げる

さあ、武器は揃いました。前回のモジュール4で作ったCIFAR-100のベースライン、その精度をこれらの武器で実際に押し上げましょう。下のColabノートブック 03_cifar100_improve.ipynb は、前回のネットワークにデータ拡張・Dropout・BatchNormを組み込んで、精度がどこまで伸びるかを試すものです。これが授業課題2(CIFAR-100の分類精度改善)の総仕上げになります。

進め方のおすすめは、武器を一つずつ足していくことです。まずデータ拡張だけを入れて学習曲線と検証精度の変化を見る。次にDropoutを加える。さらにBatchNormを入れる。一度に全部盛りにすると、何が効いたのか分からなくなります。今日学んだ「二本の曲線の乖離」を毎回チェックしながら、過学習が抑えられて検証精度が上がっていく手応えを、自分の目で確かめてください。ベースラインからどれだけ伸ばせるかが、このモジュールの実践的なゴールです。

Open in Colab CIFAR-100 改善実験 その2(Dropout / BN / DA を効かせる・授業課題2に直結)

まとめ

過学習との戦いを通して、「よく学ぶ」だけでなく「学びすぎない」ための技術を身につけました。要点を振り返ります。

  • 学習の真の目的は訓練損失の最小化ではなく、未知データへの汎化である。訓練成績と検証成績を並べて見ることが診断の基本。
  • 学習曲線で二本の曲線の乖離を読めば、過学習(訓練だけ下がり検証が上がる)と未学習(両方高止まり)を見分けられる。
  • データ拡張は、正解が変わらない範囲で画像を変換して実質的にデータを水増しし、本質的な特徴を学ばせる。推論時に使うTTAもある。
  • Dropoutはニューロンをランダムに休ませ、「弱いネットの多数決(アンサンブル)」を一つのネットワークで疑似的に実現する。
  • BatchNormは層に入るデータを平均0・分散1に揃え(センサ信号の正規化)、学習可能な γ,β\gamma,\beta で必要な分布に戻す。学習を速く安定させる。
  • これらはすべて、モデルにあえて制約を課して本質を学ばせる正則化という一つの思想でつながっている。

これで、深層学習の「学習と汎化」の一通りが揃いました。次のモジュール6では、そもそもデータが少ししかないとき、ゼロから学習する代わりに「他人が学んだ知識を借りてくる」転移学習へと進みます。少ないデータで賢く戦う、実務で最も出番の多いアプローチです。

確認クイズ

確認クイズ(0 / 5 問回答)正解 0 / 5
  1. 過学習(overfitting)を最もよく表しているのはどれですか。

  2. 学習曲線で過学習が始まったことを示す典型的なサインはどれですか。

  3. データ拡張(data augmentation)が過学習を抑える理由として最も適切なものはどれですか。

  4. Dropout の説明として正しいものはどれですか。

  5. Batch Normalization(BatchNorm)について、正しい説明はどれですか。