こしあん
2018-07-03

pandasでグループ別に統計量やヒストグラムを表示する方法

初投稿です。この記事では、pandasでグループ別に基本統計量(describe)をする方法を紹介します。

テストデータ

以下のようなデータを想定します。ある学校の3つのクラスでテストをしてみました。

  • A組は40人、平均点は60点、標準偏差は10(分布は正規分布に従うものとする)
  • B組は30人、平均点は50点、標準偏差は20
  • C組は20人、平均点は65点、標準偏差は5

このとき、「組別の得点の基本統計量」を表示する方法を考えます。また、このテストの赤点40点で、40点以上なら及第(1)、40点未満なら落第(0)とするパラメーターを導入します。つまり次のようなデータになります(スペースの関係上省略して書いています)。

student class score passed
1 A 70 1
2 A 50 1
3 B 55 1
4 B 30 0
5 C 60 1

Pythonのコードでは次のようになります。

import numpy as np
import pandas as pd
import matplotlib.pyplot as plt

student_a, student_b, student_c = 40, 30, 20

# クラス
data_classes = np.r_[np.repeat("A", student_a), np.repeat("B", student_b), np.repeat("C", student_c)]
# 得点
np.random.seed(45)
data_scores = np.r_[np.random.randn(student_a)*10+60,
                    np.random.randn(student_b)*20+50,
                    np.random.randn(student_c)*5+65]
data_scores = np.round(data_scores, decimals=1)
# PandasのDataFrameにする、40点以上は及第(1)
df_test = pd.DataFrame({"class":data_classes, "score":data_scores, "passed":(data_scores>=40).astype(int)})

グルーピングして基本統計量を表示

以下のコードでOKです。カラム(class, score, passed)が2個ならfilterは不要です。上は得点(score)の基本統計量、下は及第(passed)の基本統計量となります。

# 組別の点数の統計量(カラムが2個ならfilterなしでOK)
score_stat = df_test.filter(items=["class", "score"]).groupby("class").describe()
print(score_stat)
# 組別の及第の統計量
passed_stat = df_test.filter(items=["class", "passed"]).groupby("class").describe()
print(passed_stat)

出力は以下の通りです。

      score
      count       mean        std   min     25%    50%     75%   max
class
A      40.0  57.320000   9.948101  34.0  51.150  56.50  63.000  82.5
B      30.0  47.853333  15.559047  18.2  36.675  49.05  55.200  85.3
C      20.0  66.165000   4.734673  55.6  63.800  64.70  69.925  74.1
      passed
       count      mean       std  min  25%  50%  75%  max
class
A       40.0  0.975000  0.158114  0.0  1.0  1.0  1.0  1.0
B       30.0  0.666667  0.479463  0.0  0.0  1.0  1.0  1.0
C       20.0  1.000000  0.000000  1.0  1.0  1.0  1.0  1.0

describe()は中央値、平均値、クォンタイル値が一目瞭然なのでとても便利な関数です。この例ではB組が1/3落第しているのに対して、C組は全員合格しているのがわかります。

グルーピングしてヒストグラム

組別の得点のヒストグラムは以下のようにします。columnを省略すると、scoreとpassedが同一のグラフに表示されて見づらくなるので注意が必要です。

# 組別の点数のヒストグラム
df_test.hist(column="score", by="class", range=(0,100))
plt.show()

とても簡単でしたね。pandasは集計にとても便利なので、ぜひ活用してくださいね。

Related Posts

CIFAR-10/100のバイナリを画像ファイルに書き出す方法... CIFAR-10/100は画像分類として頻繁に用いられるデータセットですが、たまに画像ファイルでほしいことがあります。配布ページにはNumpy配列をPickleで固めたものがあり、画像ファイルとしては配布されていないので個々のファイルに書き出す方法を解説していきます。 コード まずは配布ページ...
PandasのDataFrameでグループ別にサンプルをN個抜き出す方法... 「PandasでGroupbyでグルーピングしたはいんだけど、そこからグループ別にサンプルを1個、2個…と抜き出す、SQLでよくやるやつってどうやるんだっけ?」ということが気になったので、調べました。ちゃんとした方法があります。 例題 今、中国地方と四国地方の県と面積をDataFrameにして...
Kernel-PCAのexplained_variance_ratioを求める方法... scikit-learnのPCA(主成分分析)にはexplained_variance_ratio_という、次元を削減したことでどの程度分散(データを説明できる度合い)が落ちたのかを簡単に確認できる値があります。Kernel-PCAではカーネルトリックにより、特徴量の空間が変わってしまうので、ex...
Pythonで画像のカラーヒストグラムを簡単に表示する方法... 画像で赤、緑、青の画素がどのような分布になっているかという「カラーヒストグラム」を見たいことがあります。しかしいざ探すとツールが少ないのです。Pythonならほんの数行で出せます。 PillowとPyplotでとてもお手軽 カラーヒストグラムの原理は単純で、縦横カラーチャンネルの画像を、カラー...
Pandasで複数の列を値をもとに、新しい列を任意の関数で定義する方法... Pandasで、「列A(文字列)と列B(数字)」を文字列として結合し、新しい列を定義するという操作をしたかったのですが、思ったよりも情報がなくハマったので解説していきたいと思います。 サンプルデータ 次のようなデータを定義しました。コミケのサークルスペースのデータを模したものです。 impo...

Add a Comment

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です