📚 背景知識(読んでから問題へ)
「ばらつき」を数値で表す
「平均」はデータの中心を教えてくれますが、データがどれだけ散らばっているかは教えてくれません。
例: 月収
- グループA: 30万, 30万, 30万(平均30万)
- グループB: 10万, 30万, 50万(平均30万)
どちらも平均は同じですが、グループBのほうがばらつきが大きいです。
分散(Variance)
各データが平均からどれだけ離れているか(= ズレ)を2乗して平均したもの。
分散 = Σ(データ - 平均)² / データ数
なぜ2乗するか? → マイナスのズレとプラスのズレが相殺しないように。
標準偏差(Standard Deviation)
分散の平方根。単位が元のデータと同じになるので解釈しやすい。
標準偏差 = √分散
標準偏差が小さい → データが平均に集中している
標準偏差が大きい → データが広くばらついている
外れ値(Outlier)
データの中で極端に大きいまたは小さい値。
よく使うルール: IQR(四分位範囲)法
- Q1(25パーセンタイル)と Q3(75パーセンタイル)を求める
- IQR = Q3 - Q1
- Q1 - 1.5×IQR より小さい、または Q3 + 1.5×IQR より大きい値が外れ値
📝 問題
以下の5つの問いに答えてください。コードを使わずに手計算と概念理解で答えることを目標にします(最後にPythonで確認してOK)。
データ: 7人の日次売上(万円)
[5, 7, 8, 6, 9, 7, 100]
Q1: このデータの平均を求めてください。
Q2: 外れ値に見える値はどれですか?なぜそう思いますか?(直感で答えてOK)
Q3: 外れ値を除いた6つのデータの平均を求めてください。Q1との差から、外れ値が平均に与える影響を説明してください。
Q4: IQR法を使って外れ値を判定してください。以下のヒントを使用してください。
- Q1(25%点)= 6
- Q3(75%点)= 8.5
Q5: Kaggleのコンペで外れ値を見つけたとき、あなたならどう対処しますか?(理由込みで自分の考えを書いてください。正解はありません)
🔍 ヒント(段階的開示)
ヒント1(方向性)
Q1は全部足して7で割る。Q3は外れ値(100)を除いた6つで平均を再計算する。
ヒント2(IQR法の手順)
IQR = Q3 - Q1 = 8.5 - 6 = 2.5
下限 = Q1 - 1.5 × IQR = 6 - 3.75 = 2.25
上限 = Q3 + 1.5 × IQR = 8.5 + 3.75 = 12.25
→ 2.25 未満 or 12.25 超のデータが外れ値
ヒント3(Python確認コード)
import numpy as np
data = [5, 7, 8, 6, 9, 7, 100]
# 平均
mean = np.mean(data)
# IQR
q1, q3 = np.percentile(data, [25, 75])
iqr = q3 - q1
lower = q1 - 1.5 * iqr
upper = q3 + 1.5 * iqr
# 外れ値の特定
outliers = [x for x in data if x < lower or x > upper]
✅ 模範解答
Q1: (5+7+8+6+9+7+100) / 7 = 142 / 7 ≈ 20.3万円
Q2: 100 が外れ値の候補。他の値が5〜9の範囲にあるのに対して100だけ極端に大きいため。
Q3: (5+7+8+6+9+7) / 6 = 42 / 6 = 7.0万円
→ 外れ値1つを加えるだけで平均が 7.0 → 20.3 に跳ね上がる。外れ値は平均に劇的な影響を与える。
Q4:
- IQR = 8.5 - 6 = 2.5
- 下限 = 6 - 1.5 × 2.5 = 6 - 3.75 = 2.25
- 上限 = 8.5 + 1.5 × 2.5 = 8.5 + 3.75 = 12.25
- 100 > 12.25 なので 100は外れ値 と判定される
Q5(参考回答):
外れ値を見つけたら:
- まず「データのミスか?本物の値か?」を確認する(入力エラーの可能性)
- ターゲット変数との相関を確認。外れ値が予測に重要なパターンなら除外してはいけない
- 対数変換(log変換)で影響を小さくする手段もある
- モデルによっては外れ値に強いもの(木系モデル)を選ぶ
🪜 Step-by-Step 解説
100という1つの値が、全体の平均を7.0から20.3に引き上げた。
これが「平均は外れ値に弱い」と言われる理由。中央値(7.0)は外れ値の影響を受けにくい。
IQR = データの「中央50%の幅」。外れ値の基準をデータのばらつき自体から計算するので頑健。
1.5という係数は統計的慣習(正規分布で約99.3%をカバーする)。
import numpy as np
data = [5, 7, 8, 6, 9, 7, 100]
print(f"平均(全体): {np.mean(data):.2f}")
print(f"平均(除外後): {np.mean([x for x in data if x != 100]):.2f}")
print(f"中央値: {np.median(data):.2f}")
q1, q3 = np.percentile(data, [25, 75])
iqr = q3 - q1
lower, upper = q1 - 1.5 * iqr, q3 + 1.5 * iqr
outliers = [x for x in data if x < lower or x > upper]
print(f"外れ値: {outliers}")
# 出力: 外れ値: [100]
📐 数学・統計の補足(文系向け)
パーセンタイルとは?
「下から何%の位置にあるか」を表す。
- Q1(25パーセンタイル)= データを小さい順に並べたとき、下から25%の位置の値
- Q3(75パーセンタイル)= 下から75%の位置の値
- 中央値 = Q2(50パーセンタイル)
IQRの直感的なイメージ
箱ひげ図の「箱」の高さがIQR。箱から離れすぎた点が外れ値。
🏆 Kaggleでの実践的な使い方
外れ値処理は EDA(探索的データ分析)の最重要ステップのひとつ。
# Kaggleでよく使う外れ値チェックコード
import pandas as pd
import seaborn as sns
# ボックスプロットで視覚的に確認
sns.boxplot(x=df['price'])
# IQR法で外れ値フラグを作る
Q1 = df['price'].quantile(0.25)
Q3 = df['price'].quantile(0.75)
IQR = Q3 - Q1
df['is_outlier'] = (df['price'] < Q1 - 1.5*IQR) | (df['price'] > Q3 + 1.5*IQR)
print(df['is_outlier'].value_counts())
House Pricesコンペでは、超高額物件(外れ値)を除外することでRMSEが大幅に改善した事例がある。
⚠️ よくある誤解・ミス
| 誤解・ミス | なぜ起こるか | 正しい理解 |
|---|---|---|
| 外れ値は必ず除去すべき | 「邪魔な値」と思い込む | 外れ値が本物の現象(詐欺取引など)の場合、除去すると予測性能が下がる |
| 平均だけ見て判断する | 平均が最も直感的な指標 | 外れ値に強い中央値や標準偏差も必ず確認する |
| IQRの1.5倍は絶対的な基準 | 統計的ルールを固定視 | データ・ドメインによって3倍などに変えることもある |
🚀 次のステップ
- 発展:
z-score法(平均からの標準偏差の倍数で外れ値判定)を試す - 次回予告: テーマ3「確率の基礎(確率とは何か)」または テーマ2の最終コーディング問題