📈 ステップ20: NumPyで統計計算
平均、中央値、標準偏差…NumPyで簡単に統計量を計算しよう!
Part 3で学んだ統計計算を、NumPyを使って簡単に行う方法を学びます。自分で関数を作らなくても、NumPyには便利な統計関数がたくさん用意されています。
📖 このステップで学ぶこと
・平均値(mean)、中央値(median)、標準偏差(std)
・最大値(max)、最小値(min)とその位置
・合計(sum)と累積和(cumsum)
・パーセンタイル(percentile)と四分位数
・2次元配列での統計計算(axis指定)
学習時間の目安: 2.5〜3時間
🎯 1. 基本的な統計量
データ分析で最もよく使う3つの統計量から始めましょう。
🔰 平均値を計算 – mean()
mean()(ミーン)は、データの平均値を計算します。「全部足して、個数で割る」計算を自動でやってくれます。
📝 書き方:平均値の計算
np.mean(配列)
配列.mean()
どちらの書き方でも同じ結果になります。
コード:平均値を計算する
import numpy as np
# テストの点数データ
scores = np.array([85, 92, 78, 95, 88, 90, 82])
# 平均値を計算(2つの方法)
average1 = np.mean(scores) # 方法1: np.mean()
average2 = scores.mean() # 方法2: 配列.mean()
print(f"テストの点数: {scores}")
print(f"平均点(np.mean): {average1}")
print(f"平均点(.mean): {average2}")
print(f"平均点(小数第1位): {round(average1, 1)}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
テストの点数: [85 92 78 95 88 90 82] 平均点(np.mean): 87.14285714285714 平均点(.mean): 87.14285714285714 平均点(小数第1位): 87.1
💡 コードの解説
np.mean(scores)
・NumPyの関数として平均を計算
・(85+92+78+95+88+90+82) ÷ 7 = 87.14… を自動計算
round(average1, 1)
・小数第1位で四捨五入
・見やすい数値にするときに使います
📘 中央値を計算 – median()
median()(メディアン)は、データを小さい順に並べた時の真ん中の値を返します。
📝 書き方:中央値の計算
np.median(配列)
※ 配列.median()という書き方はありません。必ずnp.median()を使います。
コード:中央値を計算する
import numpy as np
scores = np.array([85, 92, 78, 95, 88, 90, 82])
# 中央値を計算
median_value = np.median(scores)
# 並べ替えて確認
sorted_scores = np.sort(scores)
print(f"元の点数: {scores}")
print(f"並べ替え: {sorted_scores}")
print(f"中央値: {median_value}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
元の点数: [85 92 78 95 88 90 82] 並べ替え: [78 82 85 88 90 92 95] 中央値: 88.0
💡 中央値の求め方
並べ替え: [78, 82, 85, 88, 90, 92, 95]
7個のデータなので、4番目(真ん中)の88が中央値です。
データが偶数個の場合は、真ん中2つの平均になります。
📘 平均値と中央値の使い分け
この2つは似ていますが、使うべき場面が違います。外れ値(極端な値)があるかどうかで選びます。
コード:外れ値がある場合の比較
import numpy as np
# 外れ値がないデータ
normal_data = np.array([10, 20, 30, 40, 50])
print("【外れ値なし】")
print(f"データ: {normal_data}")
print(f"平均: {np.mean(normal_data)}")
print(f"中央値: {np.median(normal_data)}")
# 外れ値があるデータ
outlier_data = np.array([10, 20, 30, 40, 1000])
print("\n【外れ値あり(1000)】")
print(f"データ: {outlier_data}")
print(f"平均: {np.mean(outlier_data)}")
print(f"中央値: {np.median(outlier_data)}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
【外れ値なし】 データ: [10 20 30 40 50] 平均: 30.0 中央値: 30.0 【外れ値あり(1000)】 データ: [ 10 20 30 40 1000] 平均: 220.0 中央値: 30.0
📌 平均と中央値の使い分け
| 統計量 | 特徴 | 使う場面 |
| 平均値 | 外れ値の影響を受けやすい | データが均等に分布している時 |
| 中央値 | 外れ値の影響を受けにくい | 年収など、外れ値がある時 |
📘 標準偏差を計算 – std()
std()(スタンダード・デビエーション)は、データのばらつきを表す数値です。
📝 書き方:標準偏差の計算
np.std(配列)
配列.std()
標準偏差が小さい → データが平均の近くに集中
標準偏差が大きい → データが広く散らばっている
コード:標準偏差を比較する
import numpy as np
# ばらつきが小さいデータ(50付近に集中)
data1 = np.array([48, 49, 50, 51, 52])
# ばらつきが大きいデータ(広く散らばっている)
data2 = np.array([10, 30, 50, 70, 90])
print("【ばらつき小】")
print(f"データ: {data1}")
print(f"平均: {np.mean(data1)}")
print(f"標準偏差: {np.std(data1):.2f}")
print("\n【ばらつき大】")
print(f"データ: {data2}")
print(f"平均: {np.mean(data2)}")
print(f"標準偏差: {np.std(data2):.2f}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
【ばらつき小】 データ: [48 49 50 51 52] 平均: 50.0 標準偏差: 1.41 【ばらつき大】 データ: [10 30 50 70 90] 平均: 50.0 標準偏差: 28.28
💡 標準偏差の読み方
どちらも平均は50ですが:
・data1の標準偏差は1.41 → 平均±1.41の範囲にほぼ収まる
・data2の標準偏差は28.28 → 平均±28.28と広く散らばっている
テストで言えば、data1は「みんな同じくらいの点数」、data2は「点数の差が大きい」クラスです。
📊 2. 最大値・最小値
🔰 最大値と最小値を見つける
np.max()とnp.min()で、配列の中の最大・最小値を見つけられます。
コード:最大値と最小値を求める
import numpy as np
# 1週間の気温データ
temperatures = np.array([18.5, 21.2, 19.8, 22.5, 20.1, 17.3, 23.8])
print(f"気温データ: {temperatures}")
print()
print(f"最高気温: {np.max(temperatures)}℃")
print(f"最低気温: {np.min(temperatures)}℃")
print(f"気温の範囲: {np.max(temperatures) - np.min(temperatures)}℃")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
気温データ: [18.5 21.2 19.8 22.5 20.1 17.3 23.8] 最高気温: 23.8℃ 最低気温: 17.3℃ 気温の範囲: 6.5℃
📘 最大値・最小値の位置を見つける
「最高点は何点?」だけでなく「最高点は何番目?」を知りたいときは、argmax()とargmin()を使います。
📝 書き方:位置(インデックス)を取得
np.argmax(配列) → 最大値のインデックス
np.argmin(配列) → 最小値のインデックス
arg = argument(引数)の略。「どこにあるか」を返します。
コード:最大・最小の位置を特定
import numpy as np
# 曜日別の売上データ(万円)
sales = np.array([120, 135, 150, 145, 160, 175, 180])
days = ['月', '火', '水', '木', '金', '土', '日']
print(f"売上: {sales}")
# 最大値のインデックスを取得
max_idx = np.argmax(sales)
print(f"\n最高売上: {days[max_idx]}曜日 {sales[max_idx]}万円")
# 最小値のインデックスを取得
min_idx = np.argmin(sales)
print(f"最低売上: {days[min_idx]}曜日 {sales[min_idx]}万円")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
売上: [120 135 150 145 160 175 180] 最高売上: 日曜日 180万円 最低売上: 月曜日 120万円
💡 コードの解説
np.argmax(sales)
・最大値180があるインデックス6を返す
days[max_idx]
・days[6]で「日」を取得
sales[max_idx]
・sales[6]で180を取得
📘 2次元配列での最大・最小(axis指定)
2次元配列では、行ごとまたは列ごとに計算することができます。
📌 axisパラメータの意味
| axis | 方向 | 結果 |
| 指定なし | 全体 | 1つの値 |
| axis=0 | 縦方向(列ごと) | 各列の結果 |
| axis=1 | 横方向(行ごと) | 各行の結果 |
コード:2次元配列でaxisを使う
import numpy as np
# 3人の3科目の点数(生徒×科目)
scores = np.array([
[85, 90, 78], # 太郎(国語、数学、英語)
[92, 88, 95], # 花子
[78, 85, 82] # 次郎
])
print("点数データ:")
print(scores)
# 全体の最高点・最低点
print(f"\n全体の最高点: {np.max(scores)}")
print(f"全体の最低点: {np.min(scores)}")
# 各生徒の最高点(axis=1: 行ごと)
print(f"\n各生徒の最高点: {np.max(scores, axis=1)}")
# 各科目の最高点(axis=0: 列ごと)
print(f"各科目の最高点: {np.max(scores, axis=0)}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
点数データ: [[85 90 78] [92 88 95] [78 85 82]] 全体の最高点: 95 全体の最低点: 78 各生徒の最高点: [90 95 85] 各科目の最高点: [92 90 95]
💡 axisの覚え方
axis=0: 0番目の次元(行)を「潰す」→ 列ごとの計算
axis=1: 1番目の次元(列)を「潰す」→ 行ごとの計算
混乱したら、実際に試して結果を確認するのが一番です!
➕ 3. 合計と累積和
🔰 合計を計算 – sum()
np.sum()で、配列の全要素の合計を計算できます。
コード:合計を計算する
import numpy as np
# 1週間の売上(万円)
sales = np.array([120, 135, 150, 145, 160, 175, 180])
print(f"1週間の売上: {sales}")
print(f"合計売上: {np.sum(sales)}万円")
print(f"平均売上: {np.mean(sales):.1f}万円")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
1週間の売上: [120 135 150 145 160 175 180] 合計売上: 1065万円 平均売上: 152.1万円
📘 2次元配列の合計(axis指定)
コード:行ごと・列ごとの合計
import numpy as np
# 3店舗×5日間の売上(千円)
sales = np.array([
[120, 135, 150, 145, 160], # 店舗A
[110, 125, 140, 138, 155], # 店舗B
[115, 130, 145, 142, 158] # 店舗C
])
print("売上データ(店舗×日):")
print(sales)
# 各店舗の合計(axis=1: 行ごと)
store_total = np.sum(sales, axis=1)
print(f"\n各店舗の合計: {store_total}")
# 各日の合計(axis=0: 列ごと)
daily_total = np.sum(sales, axis=0)
print(f"各日の合計: {daily_total}")
# 全体の合計
print(f"全体の合計: {np.sum(sales)}千円")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
売上データ(店舗×日): [[120 135 150 145 160] [110 125 140 138 155] [115 130 145 142 158]] 各店舗の合計: [710 668 690] 各日の合計: [345 390 435 425 473] 全体の合計: 2068千円
📘 累積和を計算 – cumsum()
cumsum()(キュームラティブ・サム)は、累積和(だんだん足していった値)を計算します。「今までの合計」を知りたいときに使います。
📝 書き方:累積和の計算
np.cumsum(配列)
cumulative(累積の)+ sum(合計)= cumsum
各位置で「それまでの合計」を返します。
コード:累積和を計算する
import numpy as np
# 月別売上(万円)
monthly_sales = np.array([120, 135, 150, 145, 160, 175])
months = ['1月', '2月', '3月', '4月', '5月', '6月']
# 累積売上を計算
cumulative = np.cumsum(monthly_sales)
print("月別売上と累積売上:")
for month, sales, cum in zip(months, monthly_sales, cumulative):
print(f" {month}: {sales}万円(累積: {cum}万円)")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
月別売上と累積売上: 1月: 120万円(累積: 120万円) 2月: 135万円(累積: 255万円) 3月: 150万円(累積: 405万円) 4月: 145万円(累積: 550万円) 5月: 160万円(累積: 710万円) 6月: 175万円(累積: 885万円)
💡 累積和の計算の流れ
元のデータ: [120, 135, 150, 145, 160, 175]
累積和: [120, 120+135=255, 255+150=405, 405+145=550, …]
使い道:累積売上、累積来客数、累積貯金額など
📊 4. パーセンタイルと四分位数
🔰 パーセンタイルとは?
パーセンタイルは、データを小さい順に並べた時の「〇%の位置の値」です。テストの偏差値や、身長・体重の成長曲線などで使われます。
📝 書き方:パーセンタイルの計算
np.percentile(配列, パーセント値)
例:np.percentile(data, 25) → 下から25%の位置の値
コード:パーセンタイルを計算する
import numpy as np
# テストの点数(小さい順に並んでいる)
scores = np.array([65, 72, 78, 82, 85, 88, 90, 92, 95, 98])
print(f"点数: {scores}")
print()
# 各パーセンタイルを計算
p25 = np.percentile(scores, 25)
p50 = np.percentile(scores, 50)
p75 = np.percentile(scores, 75)
print(f"25パーセンタイル: {p25}点")
print(f"50パーセンタイル(中央値): {p50}点")
print(f"75パーセンタイル: {p75}点")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
点数: [65 72 78 82 85 88 90 92 95 98] 25パーセンタイル: 79.25点 50パーセンタイル(中央値): 86.5点 75パーセンタイル: 91.5点
📌 パーセンタイルの意味
| パーセンタイル | 意味 | 別名 |
| 25 | 下から25%の位置 | 第1四分位数(Q1) |
| 50 | 下から50%の位置 | 中央値(Q2) |
| 75 | 下から75%の位置 | 第3四分位数(Q3) |
📘 四分位数と四分位範囲(IQR)
四分位数を使ってIQR(四分位範囲)を計算できます。IQRはデータのばらつきを表す指標です。
コード:四分位数とIQRを計算
import numpy as np
data = np.array([12, 15, 18, 20, 22, 25, 28, 30, 35, 40, 45, 50])
# 四分位数を計算
q1 = np.percentile(data, 25) # 第1四分位数
q2 = np.percentile(data, 50) # 第2四分位数(中央値)
q3 = np.percentile(data, 75) # 第3四分位数
# 四分位範囲(IQR)を計算
iqr = q3 - q1
print(f"データ: {data}")
print()
print(f"第1四分位数(Q1): {q1}")
print(f"第2四分位数(Q2、中央値): {q2}")
print(f"第3四分位数(Q3): {q3}")
print(f"四分位範囲(IQR = Q3 - Q1): {iqr}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
データ: [12 15 18 20 22 25 28 30 35 40 45 50] 第1四分位数(Q1): 19.25 第2四分位数(Q2、中央値): 26.5 第3四分位数(Q3): 38.75 四分位範囲(IQR = Q3 - Q1): 19.5
💡 IQRの意味
IQR(四分位範囲)は「真ん中50%のデータが収まる範囲」を表します。
・IQRが小さい → データが中央に集まっている
・IQRが大きい → データが広く散らばっている
標準偏差と違い、外れ値の影響を受けにくいのが特徴です。
📘 複数のパーセンタイルを一度に計算
コード:複数のパーセンタイルを一度に取得
import numpy as np
scores = np.array([55, 62, 68, 72, 75, 78, 82, 85, 88, 90, 92, 95, 98])
# 複数のパーセンタイルをリストで指定
percentiles = np.percentile(scores, [10, 25, 50, 75, 90])
print(f"点数: {scores}")
print()
print(f"10パーセンタイル: {percentiles[0]}点")
print(f"25パーセンタイル: {percentiles[1]}点")
print(f"50パーセンタイル(中央値): {percentiles[2]}点")
print(f"75パーセンタイル: {percentiles[3]}点")
print(f"90パーセンタイル: {percentiles[4]}点")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
点数: [55 62 68 72 75 78 82 85 88 90 92 95 98] 10パーセンタイル: 63.2点 25パーセンタイル: 72.0点 50パーセンタイル(中央値): 82.0点 75パーセンタイル: 90.0点 90パーセンタイル: 94.0点
🔢 5. その他の便利な統計関数
📘 分散を計算 – var()
var()(バリアンス)は分散を計算します。標準偏差の2乗です。
コード:分散と標準偏差の関係
import numpy as np
data = np.array([10, 20, 30, 40, 50])
print(f"データ: {data}")
print(f"平均: {np.mean(data)}")
print(f"分散: {np.var(data)}")
print(f"標準偏差: {np.std(data)}")
print()
print(f"確認: 標準偏差の2乗 = {np.std(data) ** 2}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
データ: [10 20 30 40 50] 平均: 30.0 分散: 200.0 標準偏差: 14.142135623730951 確認: 標準偏差の2乗 = 200.0
📘 条件を満たす要素をカウント – count_nonzero()
count_nonzero()は、条件を満たす要素の数を数えます。
コード:条件を満たす要素を数える
import numpy as np
# テストの点数
scores = np.array([95, 72, 88, 91, 65, 78, 85])
# 80点以上の人数をカウント
passed = np.count_nonzero(scores >= 80)
total = len(scores)
print(f"点数: {scores}")
print()
print(f"合格者(80点以上): {passed}人 / {total}人")
print(f"合格率: {passed / total * 100:.1f}%")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
点数: [95 72 88 91 65 78 85] 合格者(80点以上): 4人 / 7人 合格率: 57.1%
💡 コードの解説
scores >= 80
・各要素が80以上かをTrue/Falseで返す
・[True, False, True, True, False, False, True]
np.count_nonzero()
・True(= 0でない)の数を数える → 4
📘 データを標準化する
データを平均0、標準偏差1に変換することを標準化(Standardization)といいます。異なるスケールのデータを比較したいときに使います。
📝 書き方:標準化の公式
標準化した値 = (元の値 – 平均) / 標準偏差
この計算で、どんなデータも「平均0、標準偏差1」の同じスケールになります。
コード:データを標準化する
import numpy as np
data = np.array([10, 20, 30, 40, 50])
print(f"元のデータ: {data}")
print(f"平均: {np.mean(data)}")
print(f"標準偏差: {np.std(data)}")
# 標準化
mean = np.mean(data)
std = np.std(data)
standardized = (data - mean) / std
print()
print(f"標準化後: {standardized}")
print(f"標準化後の平均: {np.mean(standardized)}")
print(f"標準化後の標準偏差: {np.std(standardized)}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
元のデータ: [10 20 30 40 50] 平均: 30.0 標準偏差: 14.142135623730951 標準化後: [-1.41421356 -0.70710678 0. 0.70710678 1.41421356] 標準化後の平均: 0.0 標準化後の標準偏差: 1.0
💡 標準化はいつ使う?
異なる単位のデータを比較するときに使います。
例:身長(cm)と体重(kg)を同じスケールで比較
例:テストの点数と年収を同じ基準で評価
機械学習では、標準化は前処理の定番です!
📊 6. 実践:データの要約統計量
📘 データの基本統計量を一覧表示
実際のデータ分析では、まず基本統計量を確認します。NumPyの関数を組み合わせて、データの全体像を把握しましょう。
コード:統計サマリーを作成
import numpy as np
# テストの点数データ
scores = np.array([55, 62, 68, 72, 75, 78, 82, 85, 88, 90, 92, 95, 98])
print("📊 テスト結果の統計")
print("=" * 40)
print(f"データ数: {len(scores)}人")
print(f"合計点: {np.sum(scores)}点")
print(f"平均点: {np.mean(scores):.1f}点")
print(f"中央値: {np.median(scores):.1f}点")
print(f"最高点: {np.max(scores)}点")
print(f"最低点: {np.min(scores)}点")
print(f"範囲: {np.max(scores) - np.min(scores)}点")
print(f"標準偏差: {np.std(scores):.2f}点")
print()
print(f"第1四分位数(Q1): {np.percentile(scores, 25):.1f}点")
print(f"第3四分位数(Q3): {np.percentile(scores, 75):.1f}点")
iqr = np.percentile(scores, 75) - np.percentile(scores, 25)
print(f"四分位範囲(IQR): {iqr:.1f}点")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
📊 テスト結果の統計 ======================================== データ数: 13人 合計点: 1040点 平均点: 80.0点 中央値: 82.0点 最高点: 98点 最低点: 55点 範囲: 43点 標準偏差: 12.49点 第1四分位数(Q1): 72.0点 第3四分位数(Q3): 90.0点 四分位範囲(IQR): 18.0点
📘 複数グループの比較
コード:2つのクラスを比較
import numpy as np
# クラスAとクラスBの点数
class_a = np.array([85, 90, 78, 92, 88, 95, 82, 87, 91, 89])
class_b = np.array([72, 68, 75, 70, 78, 74, 76, 69, 73, 71])
print("クラスA vs クラスB の比較")
print("=" * 50)
# 比較表示
print(f"{'統計量':<12} {'クラスA':>10} {'クラスB':>10}")
print("-" * 50)
print(f"{'人数':<12} {len(class_a):>10} {len(class_b):>10}")
print(f"{'平均点':<12} {np.mean(class_a):>10.1f} {np.mean(class_b):>10.1f}")
print(f"{'中央値':<12} {np.median(class_a):>10.1f} {np.median(class_b):>10.1f}")
print(f"{'最高点':<12} {np.max(class_a):>10} {np.max(class_b):>10}")
print(f"{'最低点':<12} {np.min(class_a):>10} {np.min(class_b):>10}")
print(f"{'標準偏差':<12} {np.std(class_a):>10.2f} {np.std(class_b):>10.2f}")
※ 画面が小さい場合は、コードブロックを横にスクロールできます
実行結果
クラスA vs クラスB の比較 ================================================== 統計量 クラスA クラスB -------------------------------------------------- 人数 10 10 平均点 88.7 72.6 中央値 88.5 72.5 最高点 95 78 最低点 78 68 標準偏差 4.64 3.06
💡 この比較から分かること
・クラスAの方が平均・中央値ともに高い
・クラスAの標準偏差は4.64、クラスBは3.06
→ クラスBの方がばらつきが小さい(点数が揃っている)
・両クラスとも平均と中央値がほぼ同じ → 外れ値が少ない
📝 練習問題
ここまで学んだことを、実際に手を動かして確認しましょう。
問題1:基本的な統計量の計算(初級)
📋 問題
以下の配列の平均、中央値、最大値、最小値を計算してください。
data = [45, 52, 61, 48, 55, 58, 50, 47, 53, 49]
解答例を見る
コード
import numpy as np
data = np.array([45, 52, 61, 48, 55, 58, 50, 47, 53, 49])
print(f"データ: {data}")
print()
print(f"平均: {np.mean(data)}")
print(f"中央値: {np.median(data)}")
print(f"最大値: {np.max(data)}")
print(f"最小値: {np.min(data)}")
実行結果
データ: [45 52 61 48 55 58 50 47 53 49] 平均: 51.8 中央値: 51.0 最大値: 61 最小値: 45
問題2:累積和の計算(初級)
📋 問題
月別の貯金額 [30000, 25000, 35000, 40000, 30000] を配列にして、累積貯金額を計算してください。
解答例を見る
コード
import numpy as np
monthly_savings = np.array([30000, 25000, 35000, 40000, 30000])
cumulative = np.cumsum(monthly_savings)
print(f"月別貯金額: {monthly_savings}")
print(f"累積貯金額: {cumulative}")
print()
for i, (monthly, total) in enumerate(zip(monthly_savings, cumulative), 1):
print(f"{i}ヶ月目: {monthly:,}円(累積: {total:,}円)")
実行結果
月別貯金額: [30000 25000 35000 40000 30000] 累積貯金額: [ 30000 55000 90000 130000 160000] 1ヶ月目: 30,000円(累積: 30,000円) 2ヶ月目: 25,000円(累積: 55,000円) 3ヶ月目: 35,000円(累積: 90,000円) 4ヶ月目: 40,000円(累積: 130,000円) 5ヶ月目: 30,000円(累積: 160,000円)
問題3:2次元配列での統計計算(中級)
📋 問題
以下の3人×3科目の点数データがあります。各生徒の平均点と、各科目の平均点を計算してください。
scores = [[80, 75, 90], [85, 92, 88], [78, 82, 85]]
解答例を見る
コード
import numpy as np
scores = np.array([
[80, 75, 90], # 太郎
[85, 92, 88], # 花子
[78, 82, 85] # 次郎
])
print("点数データ:")
print(scores)
# 各生徒の平均(axis=1: 行ごと)
student_avg = np.mean(scores, axis=1)
print("\n各生徒の平均点:")
students = ['太郎', '花子', '次郎']
for name, avg in zip(students, student_avg):
print(f" {name}: {avg:.1f}点")
# 各科目の平均(axis=0: 列ごと)
subject_avg = np.mean(scores, axis=0)
print("\n各科目の平均点:")
subjects = ['国語', '数学', '英語']
for subject, avg in zip(subjects, subject_avg):
print(f" {subject}: {avg:.1f}点")
実行結果
点数データ: [[80 75 90] [85 92 88] [78 82 85]] 各生徒の平均点: 太郎: 81.7点 花子: 88.3点 次郎: 81.7点 各科目の平均点: 国語: 81.0点 数学: 83.0点 英語: 87.7点
問題4:四分位数の計算(中級)
📋 問題
以下のデータの第1四分位数、中央値、第3四分位数、四分位範囲(IQR)を計算してください。
data = [12, 15, 18, 20, 22, 25, 28, 30, 32, 35, 38, 40, 45, 50, 55]
解答例を見る
コード
import numpy as np
data = np.array([12, 15, 18, 20, 22, 25, 28, 30, 32, 35, 38, 40, 45, 50, 55])
q1 = np.percentile(data, 25)
q2 = np.percentile(data, 50)
q3 = np.percentile(data, 75)
iqr = q3 - q1
print(f"データ: {data}")
print()
print(f"第1四分位数(Q1): {q1}")
print(f"中央値(Q2): {q2}")
print(f"第3四分位数(Q3): {q3}")
print(f"四分位範囲(IQR): {iqr}")
実行結果
データ: [12 15 18 20 22 25 28 30 32 35 38 40 45 50 55] 第1四分位数(Q1): 21.0 中央値(Q2): 30.0 第3四分位数(Q3): 41.25 四分位範囲(IQR): 20.25
問題5:条件付き統計(上級)
📋 問題
以下の点数データから、80点以上の点数だけを抽出して、その平均、最大値、最小値、個数を計算してください。
scores = [95, 72, 88, 91, 65, 78, 85, 92, 70, 87, 83, 76, 90]
解答例を見る
コード
import numpy as np
scores = np.array([95, 72, 88, 91, 65, 78, 85, 92, 70, 87, 83, 76, 90])
# 80点以上を抽出
high_scores = scores[scores >= 80]
print(f"全体の点数: {scores}")
print(f"80点以上: {high_scores}")
print()
print(f"80点以上の統計:")
print(f" 個数: {len(high_scores)}人")
print(f" 平均: {np.mean(high_scores):.1f}点")
print(f" 最高: {np.max(high_scores)}点")
print(f" 最低: {np.min(high_scores)}点")
print(f" 割合: {len(high_scores) / len(scores) * 100:.1f}%")
実行結果
全体の点数: [95 72 88 91 65 78 85 92 70 87 83 76 90] 80点以上: [95 88 91 85 92 87 83 90] 80点以上の統計: 個数: 8人 平均: 88.9点 最高: 95点 最低: 83点 割合: 61.5%
問題6:データの標準化(上級)
📋 問題
以下のデータを標準化(平均0、標準偏差1に変換)してください。標準化後の平均と標準偏差も確認してください。
data = [20, 25, 30, 35, 40, 45, 50]
解答例を見る
コード
import numpy as np
data = np.array([20, 25, 30, 35, 40, 45, 50])
print(f"元のデータ: {data}")
print(f"元の平均: {np.mean(data)}")
print(f"元の標準偏差: {np.std(data)}")
# 標準化: (値 - 平均) / 標準偏差
mean = np.mean(data)
std = np.std(data)
standardized = (data - mean) / std
print()
print(f"標準化後: {standardized}")
print(f"標準化後の平均: {np.mean(standardized):.10f}")
print(f"標準化後の標準偏差: {np.std(standardized)}")
実行結果
元のデータ: [20 25 30 35 40 45 50] 元の平均: 35.0 元の標準偏差: 10.0 標準化後: [-1.5 -1. -0.5 0. 0.5 1. 1.5] 標準化後の平均: 0.0000000000 標準化後の標準偏差: 1.0
🎯 このステップのまとめ
✅ 学んだこと
✓ np.mean()で平均値を計算できる
✓ np.median()で中央値を計算できる
✓ np.std()で標準偏差を計算できる
✓ np.max()/np.min()で最大値・最小値を見つけられる
✓ np.argmax()/np.argmin()で位置を見つけられる
✓ np.sum()で合計、np.cumsum()で累積和を計算できる
✓ np.percentile()でパーセンタイルを計算できる
✓ axisパラメータで行ごと・列ごとの計算ができる
💡 次のステップに進む前に確認
以下のことができるようになったか確認しましょう:
□ 基本的な統計量(平均、中央値、標準偏差)を計算できる
□ 2次元配列でaxisを使って計算できる
□ 累積和の使い方がわかる
□ パーセンタイルと四分位数を計算できる
これらができたら、次のステップに進みましょう!
❓ よくある質問
Q1: 平均と中央値はどう使い分けますか?
A: 外れ値がない場合は平均、外れ値がある場合は中央値を使います。例えば、年収データなど極端に大きい値がある場合は、中央値の方が実態を表します。
Q2: 標準偏差と分散の違いは?
A: 標準偏差は分散の平方根です。標準偏差は元のデータと同じ単位なので解釈しやすいです。通常は標準偏差を使います。
Q3: axisの0と1はどう覚えればいいですか?
A: axis=0は縦方向(列ごと)、axis=1は横方向(行ごと)です。「axis=0は行を潰す」「axis=1は列を潰す」と覚えると良いでしょう。
Q4: パーセンタイルは何に使いますか?
A: データの分布を理解するために使います。「上位10%」「下位25%」など、相対的な位置を知りたい時に便利です。
Q5: 累積和はどんな時に使いますか?
A: 「今までの合計」を知りたい時に使います。月別売上の累積、累積来客数、累積貯金額など、時系列データで「積み上げ」を見たい場合に便利です。
学習メモ
Pythonデータ分析入門 - Step 20