(1時間4,000円の伴走型ビデオチャット指導も受付中!)
Pythonで学ぶデータ圧縮の魔法:主成分分析 (PCA) の基礎から実践まで
![]()
【Hiroki】
Yukiさん、こんにちは。最近、機械学習の勉強を始めているんですけど、データの種類……「次元」っていうんでしたっけ? それが多すぎると、どう扱っていいかわからなくなっちゃうんです。調べたら「主成分分析(PCA)」がいいって聞いたんですけど、これって具体的に何をどうするものなんですか?
![]()
【Yuki】
Hirokiくん、こんにちは。ふふ、データの次元が増えると、人間には直感的に理解しづらくなってしまいますよね。主成分分析……PCA(Principal Component Analysis)は、そんな複雑に絡み合ったデータを整理して、大切な「本質」だけを取り出すための魔法のような手法なんです。
わたしも、複雑なものをシンプルにまとめる作業は好きですよ。今日は、Pythonを使ってどうやってPCAを行うのか、ゆっくりとお話ししていければいいなと思います……。
PCAとは何か?:情報の「重なり」を整理する
![]()
【Hiroki】
「情報の重なりを整理する」っていうのは、どういうイメージなんでしょう?
![]()
【Yuki】
そうですね……。たとえば、Hirokiくんの身長と体重、そして座高のデータがあるとします。これらって、お互いに関係がありそう(相関がある)だと思いませんか?
![]()
【Hiroki】
あ、確かに。身長が高い人は、体重も重かったり、座高も高かったりする傾向がありそうですね。
![]()
【Yuki】
その通りです。これらはバラバラのデータのように見えて、実は「体の大きさ」という一つの大きな共通した情報を、別々の角度から見ているだけかもしれません。
PCAは、こうした相関のあるたくさんの変数から、お互いに無関係な新しい変数(主成分)を作り出す手法なんです。一番大事な情報を「第1主成分」、その次に大事な情報を「第2主成分」……というふうに、情報の重要度順に並べ替えてくれるんですよ。
PCAの仕組み:一番「変化」が激しい方向を見つける
![]()
【Hiroki】
具体的に、どうやってその「大事な情報」を見つけているんですか?
![]()
【Yuki】
一言で言うと、「データが一番広く散らばっている方向」を探しているんです。データが一番広がっている方向こそが、そのデータの特徴を一番よく表していると考えられるからですね。
たとえば、目の前に複雑な形をしたオブジェがあると想像してみてください。そのオブジェの「影」を壁に映すとき、一番その形の特徴が伝わる角度ってありますよね。影という2次元の情報に落とし込んでも、元の3次元の姿が想像できるような……。
わたしは、そんなふうに情報のシルエットを綺麗に整えて、本質を際立たせるPCAのプロセスに、少しだけ美しさを感じてしまいます。
Pythonでの実践:Scikit-learnを使った実装
![]()
【Hiroki】
シルエット……なるほど。実際にPythonでやってみたいです! どんなライブラリを使えばいいんでしょうか?
![]()
【Yuki】
Pythonなら、scikit-learnというライブラリを使うのが一般的だと思います。今回は、有名な「アヤメ(Iris)」のデータセットを使って、4次元のデータを2次元に圧縮してみましょう。まずは必要なものをインポートしますね。
import pandas as pd
from sklearn.datasets import load_iris
from sklearn.decomposition import PCA
from sklearn.preprocessing import StandardScaler
import matplotlib.pyplot as plt
# データの読み込み
iris = load_iris()
df = pd.DataFrame(iris.data, columns=iris.feature_names)
print("元のデータの次元:", df.shape)
![]()
【Hiroki】
まずは普通にデータを読み込むんですね。このiris.dataには「がくの長さ」とか「花弁の幅」とか、4つの特徴量が入っているから4次元なんですね。
データの前処理:標準化の重要性
![]()
【Yuki】
はい。でも、PCAをする前に、とっても大切な工程があるんです。それが「標準化」です。
![]()
【Hiroki】
ヒョウジュンカ……?
![]()
【Yuki】
データの単位を揃える作業のことですね。たとえば、あるデータが「メートル」で、もう一方が「ミリメートル」だと、数字の大きさが全然違ってしまいます。PCAは「データの散らばり(分散)」を重視するので、単位が違うと、数字が大きい方の変数が不当に「重要」だと判断されてしまうかもしれないんです。
![]()
【Hiroki】
それは困りますね。公平に判断してもらうために、スケールを合わせる必要があるんだ。
![]()
【Yuki】
その通りです。StandardScalerを使うと、平均を0、分散を1に変換してくれますよ。
# データの標準化
scaler = StandardScaler()
df_scaled = scaler.fit_transform(df)
PCAの実行と結果の確認
![]()
【Yuki】
準備ができたら、いよいよPCAを実行してみましょう。4次元から2次元に圧縮してみますね。
# PCAのインスタンスを作成(2次元に圧縮)
pca = PCA(n_components=2)
# 学習と適用
pca_features = pca.fit_transform(df_scaled)
# 結果をデータフレームにする
df_pca = pd.DataFrame(
pca_features,
columns=["第1主成分", "第2主成分"]
)
print("圧縮後のデータの次元:", df_pca.shape)
![]()
【Hiroki】
わ、本当に2列(2次元)になりましたね!
可視化による理解:3次元から2次元へ
![]()
【Yuki】
さて、ここからが楽しいところです。もともと4次元だったデータはグラフに描けませんでしたが、2次元になったので平面にプロットできます。
plt.figure(figsize=(8, 6))
colors = ["red", "blue", "green"]
for i, label in enumerate(iris.target_names):
condition = (iris.target == i)
plt.scatter(
df_pca.loc[condition, "第1主成分"],
df_pca.loc[condition, "第2主成分"],
label=label,
color=colors[i],
alpha=0.7
)
plt.xlabel("First Principal Component")
plt.ylabel("Second Principal Component")
plt.legend()
plt.title("PCA of Iris Dataset")
plt.show()
![]()
【Hiroki】
すごい! 3種類のアヤメが、綺麗に分かれてプロットされていますね。
![]()
【Yuki】
そうなんです。4つの情報を2つにギュッと凝縮しても、これだけ種類ごとの特徴を維持できているということなんです。情報を削ぎ落としてシンプルにしたのに、本質は失われていない……なんだか、不思議な感覚になりませんか?
寄与率を確認する:どれだけ情報を残せたか
![]()
【Hiroki】
でも、4つを2つに減らしたってことは、少しは情報が消えちゃってるんですよね?
![]()
【Yuki】
ええ、その通りです。どのくらいの割合の情報を保持できているかを「寄与率(explained variance ratio)」と呼びます。これを確認することで、そのPCAがどれだけ上手くいったかを知ることができますよ。
# 寄与率の確認
evr = pca.explained_variance_ratio_
print(f"第1主成分の寄与率: {evr[0]:.3f}")
print(f"第2主成分の寄与率: {evr[1]:.3f}")
print(f"累計寄与率: {sum(evr):.3f}")
![]()
【Hiroki】
累計寄与率が0.95とかだったら、元の情報の95%をたった2つの主成分で説明できている、っていう意味になるんですね。
![]()
【Yuki】
物知りですね、Hirokiくん。その通りです。多くの場合、累計寄与率が80%〜90%を超えていれば、十分にデータの性質を表せていると判断されることが多いと思います。
PCAを使う際の注意点:意味の解釈が難しくなる?
![]()
【Hiroki】
これだけ便利なら、どんな時でもPCAを使えばいい気がしますけど、何か弱点はあるんですか?
![]()
【Yuki】
そうですね……。一番のデメリットは、「新しく作られた変数(主成分)が、具体的に何を意味しているのか分からなくなる」ことかもしれません。
![]()
【Hiroki】
あ、そっか。「第1主成分」と言われても、それが「がくの長さ」なのか「花弁の幅」なのか、はっきり言えないんですね。
![]()
【Yuki】
はい。複数の変数を混ぜ合わせて作っているので、「なんとなくサイズ感を表している成分かな?」といった推測はできても、厳密な意味付けは難しいんです。
なので、単に予測精度を上げたい時や、データを可視化したい時には向いていますが、どの変数が結果にどう影響しているかを詳しく分析したい時には、少し注意が必要かもしれませんね。
![]()
【Hiroki】
なるほど。使い所を見極めるのが大事なんですね。
![]()
【Yuki】
ええ。複雑なものをシンプルにするのは、とても勇気がいることだと思います。でも、情報のノイズをそぎ落とすことで、夜の静寂の中で星を見つけるように、データの中に隠れた真実が見えてくることもある……わたしはそう信じています。
PCAについて、少しはイメージが湧きましたか?
![]()
【Hiroki】
はい! 思っていたよりずっと身近な技術に感じられました。Pythonのコードもシンプルですし、自分のデータでも試してみます。Yukiさん、ありがとうございました!
![]()
【Yuki】
どういたしまして。Hirokiくんの学習が、少しでも楽しいものになると嬉しいです。また分からないことがあったら、いつでも聞いてくださいね。……ふふ、応援しています。
参考文献・関連リンク - Scikit-learn PCA Documentation - Scikit-learn StandardScaler Documentation - Pythonデータサイエンスハンドブック (O'Reilly Japan)
この記事では基礎を解説しましたが、実務においては「もっと複雑なデータを扱いたい」「独自のシステムに組み込みたい」といった、個別の課題に直面することも多いはずです。
「自分で書く時間は最小限に抑え、プロの品質でツールを完成させたい」という方は、ぜひ一度ご相談ください。
- 専門家の知見に基づいた、保守性の高いコード設計
- AIの専門家による、Gemini API等の最新AIを組み合わせた高度な自動化
- ChatGPT等が生成したコードのデバッグ・最適化
「教わる」だけでなく「形にする」パートナーとして、フリーランスエンジニアのmei_13が最短ルートでの解決をサポートします。
初心者から始められるPythonレッスン
● 月額4,000円で質問し放題!!
● 完全オンライン
● 翌日までには必ず返信
● 挫折しない独自の学習メソッド
● 圧倒的高評価!!
● テキストベースで時間を選ばない
● 4,000円/60分の伴走型ビデオチャット指導も可能
● 高品質なサンプルコード
詳細はこちら

