【機械学習入門 第3回】これはAかBか?Scikit-learnで分類(Classification)モデルに挑戦しよう(アヤメ品種分類編)
「数値の予測はできたけど、次はカテゴリを予測したい!」
「このメールは『迷惑メール』か『通常メール』か、どうやって判断させるの?」
「ロジスティック回帰って名前なのに分類? k近傍法って何?」
こんにちは! AI・機械学習探検隊、隊長のPythonistaです! 前回の第2回では、「回帰」モデルを使って住宅価格という連続する数値を予測することに成功しましたね。データから未来の数値を導き出す、機械学習のパワーを実感できたのではないでしょうか。
シリーズ第3回の今回は、機械学習のもう一つの大きな柱、「分類 (Classification)」に挑戦します! 分類とは、データがどのカテゴリ(クラス)に属するかを予測するタスクです。「迷惑メールか否か」「画像に写っているのは犬か猫か」「この顧客は購入するかしないか」など、世の中の多くの問題は分類問題として捉えることができます。
今回は、機械学習の世界で「Hello, World!」として非常に有名な**アヤメ(Iris)のデータセット**を題材に、
- 名前に反して分類が得意な「ロジスティック回帰」
- 「ご近所さん」に倣う直感的なアルゴリズム「k近傍法 (k-NN)」
という2つの代表的な分類モデルを構築していきます。さあ、データを見てカテゴリを当てる、賢いモデル作りを始めましょう!
1. 準備:ライブラリのインポート
今回も、データ分析と可視化でおなじみのライブラリたちをインポートしておきます。
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
import seaborn as sns
# Scikit-learnから必要なモジュールをインポート
from sklearn.datasets import load_iris
from sklearn.model_selection import train_test_split
from sklearn.linear_model import LogisticRegression # ロジスティック回帰
from sklearn.neighbors import KNeighborsClassifier # k近傍法
from sklearn.metrics import accuracy_score # 性能評価のため(今回は軽く触れます)
# 見た目の設定
sns.set_theme(style="whitegrid", palette="pastel")
plt.rcParams['font.family'] = 'IPAexGothic' # 日本語フォント設定
2. 分類(Classification)とは? 回帰との違い
分類 (Classification) とは、教師あり学習の一種で、データがどの**カテゴリ(クラス)**に属するかを予測するタスクです。
前回の**回帰 (Regression)** との違いをしっかり理解しましょう。
- 回帰: 予測する値が**連続的な数値**(例: 価格 150.5万円, 気温 23.8度)。
- 分類: 予測する値が**離散的なカテゴリ**(例: 「犬」「猫」「鳥」、あるいは「迷惑メール」「通常メール」の2択)。
「数値を当てる」のが回帰、「ラベルを当てる」のが分類、と考えると分かりやすいですね。
3. データを知る:アヤメ(Iris)データセット
今回は、分類問題の入門として最も有名な「アヤメ(Iris)のデータセット」を使います。このデータセットには、3種類のアヤメ(setosa, versicolor, virginica)それぞれ50個分について、4つの特徴量(がくの長さ・幅、花びらの長さ・幅)が記録されています。私たちの目標は、これらの4つの特徴量から、そのアヤヤメがどの品種なのかを当てるモデルを作ることです。
3.1. データの読み込みと探索
# アヤメデータセットをロード
iris = load_iris()
# Pandas DataFrameに変換して探索しやすくする
df = pd.DataFrame(data=iris.data, columns=iris.feature_names)
df['species'] = iris.target_names[iris.target] # ターゲット(0,1,2)を品種名に変換
print("--- アヤメデータセットの概要 (info) ---")
df.info()
print("\n--- 最初の5行 (head) ---")
print(df.head())
print("\n--- 品種ごとのデータ数 ---")
print(df['species'].value_counts())
3.2. データの可視化
Seabornのpairplot
を使うと、すべての特徴量の組み合わせの散布図と、各特徴量のヒストグラムを一度に描画でき、データの関係性を視覚的に把握するのに非常に便利です。
# 品種(species)ごとに色分けしてペアプロットを描画
sns.pairplot(df, hue='species', palette='husl')
plt.suptitle('アヤメデータセットのペアプロット', y=1.02)
plt.show()
このグラフを見ると、例えば花びらの長さ(petal length)と幅(petal width)を使えば、品種をかなりうまく分離できそうなことが見て取れますね。機械学習モデルは、このような関係性を数値的に学習していきます。
4. データ準備とモデル構築
前回同様、データを準備し、2種類のモデルを構築・訓練していきます。
4.1. 訓練データとテストデータへの分割
まずは、特徴量X
とターゲットy
を定義し、train_test_split
でデータを分割します。
X = iris.data
y = iris.target
X_train, X_test, y_train, y_test = train_test_split(X, y, test_size=0.3, random_state=42, stratify=y)
# stratify=y を指定すると、訓練データとテストデータのクラスの比率を元データと同じに保ってくれる
print(f"訓練データの形状: {X_train.shape}")
print(f"テストデータの形状: {X_test.shape}")
stratify=y
は、分類問題において各クラスのデータが偏らないように分割するための重要なオプションです。
4.2. モデル1:ロジスティック回帰 (Logistic Regression)
ロジスティック回帰は、「回帰」という名前がついていますが、実際には分類問題で最もよく使われる基本的なアルゴリズムの一つです。データが特定のクラスに属する「確率」を計算し、その確率が最も高いクラスに分類します。内部的には、線形回帰のように特徴量の重み付けを行いますが、最終的な出力をシグモイド関数という関数で0から1の間の確率に変換するのが特徴です。
# 1. モデルのインスタンス化
log_reg = LogisticRegression(max_iter=200) # max_iterは計算の反復回数の上限
# 2. モデルの学習
log_reg.fit(X_train, y_train)
# 3. テストデータで予測
y_pred_lr = log_reg.predict(X_test)
print("\n--- ロジスティック回帰による予測 (最初の5件) ---")
print(f"予測: {y_pred_lr[:5]}")
print(f"正解: {y_test[:5]}")
4.3. モデル2:k近傍法 (k-Nearest Neighbors, k-NN)
k近傍法 (k-NN) は、非常に直感的で理解しやすいアルゴリズムです。その考え方は「ご近所さんの多数決で決める」というものです。
- 新しいデータ点が与えられると、その点から最も近い訓練データを「k個」見つけ出します。(kは私たちが決める数、例えば3や5)
- そのk個のデータの中で、最も多数派だったクラスを、新しいデータ点のクラスとして予測します。
非常にシンプルですが、多くの場合でうまく機能します。
# 1. モデルのインスタンス化 (近傍の数kを3に設定)
knn = KNeighborsClassifier(n_neighbors=3)
# 2. モデルの学習
knn.fit(X_train, y_train)
# 3. テストデータで予測
y_pred_knn = knn.predict(X_test)
print("\n--- k近傍法 (k-NN) による予測 (最初の5件) ---")
print(f"予測: {y_pred_knn[:5]}")
print(f"正解: {y_test[:5]}")
5. パフォーマンスの初見:正解率 (Accuracy) を見てみよう
モデルの性能を評価する方法は次回詳しく解説しますが、分類モデルで最も基本的な指標である**正解率 (Accuracy)** を見てみましょう。これは、全データのうち、どれくらいの割合を正しく予測できたかを示す指標です。
Scikit-learnでは、モデルの.score()
メソッドを呼び出すか、accuracy_score()
関数を使うことで簡単に計算できます。
# ロジスティック回帰の正解率
accuracy_lr = log_reg.score(X_test, y_test)
print(f"\nロジスティック回帰の正解率: {accuracy_lr:.4f}")
# k近傍法の正解率 (accuracy_score関数を使う例)
accuracy_knn = accuracy_score(y_test, y_pred_knn)
print(f"k近傍法 (k=3) の正解率: {accuracy_knn:.4f}")
実行結果 (例 - random_stateにより固定):
ロジスティック回帰の正解率: 1.0000
k近傍法 (k=3) の正解率: 1.0000
アヤメのデータセットは比較的簡単な問題なので、どちらのモデルも非常に高い正解率(この場合は100%!)を達成できました。しかし、正解率だけを見てモデルの性能を判断するのは、実は危険な場合があります。
まとめと次回予告
今回は、機械学習入門シリーズの第3回として、データをカテゴリに分ける「分類」に挑戦しました。
- 数値を予測する「回帰」と、カテゴリを予測する「分類」の違いを理解した。
- 有名なアヤメ(Iris)データセットを使い、データの探索と可視化を行った。
- 代表的な分類アルゴリズムである「ロジスティック回帰」と「k近傍法」の2つのモデルを構築し、予測を行った。
- モデルの性能を測る最も基本的な指標である正解率を計算した。
これで、あなたは数値予測だけでなく、カテゴリ分類という、機械学習におけるもう一つの大きな柱を立てることができました!
さて、「正解率100%なんてすごい!もう完璧なモデルができたんだ!」と思ってしまうかもしれません。しかし、現実はそう単純ではありません。「もし、クラスのデータ数に偏りがあったら?」「どんな間違い方をしているか、詳しく知りたい!」など、正解率だけでは見えてこないモデルの側面があります。
次回、第4回では、まさにその**「モデルの性能評価」**を深掘りします! 作ったモデルが良いものかどうかを多角的に判断するための指標、特に**「混同行列 (Confusion Matrix)」**、そして**「適合率 (Precision)」「再現率 (Recall)」**といった、よりプロフェッショナルな評価方法を学びます。モデルの真の実力を測るための「健康診断」テクニックです。お楽しみに!
コメント
コメントを投稿