Matplotlibを使用して、事前にカウントされたデータのヒストグラムをプロットしたいと思います。たとえば、生データがあるとします
data = [1, 2, 2, 3, 4, 5, 5, 5, 5, 6, 10]
このデータがあれば、
pylab.hist(data, bins=[...])
ヒストグラムをプロットします。
私の場合、データは事前にカウントされており、辞書として表されています。
counted_data = {1: 1, 2: 2, 3: 1, 4: 1, 5: 4, 6: 1, 10: 1}
理想的には、この事前にカウントされたデータを生のデータを渡したかのように、ビンの幅やプロット範囲などを制御できるヒストグラム関数に渡したいと思います。回避策として、カウントを生データに拡大しています。
data = list(chain.from_iterable(repeat(value, count)
for (value, count) in counted_data.iteritems()))
これはcounted_data
には、数百万のデータポイントのカウントが含まれます。
Matplotlibを使用して、事前にカウントされたデータからヒストグラムを作成する簡単な方法はありますか?
または、事前にビニングされたデータを棒グラフ化するのが最も簡単な場合、アイテムごとのカウントをビニングされたカウントに「ロールアップ」する便利な方法はありますか?
私は pyplot.hist のweights
オプションを使用して、各キーの値に重みを付け、必要なヒストグラムを作成しました。
pylab.hist(counted_data.keys(), weights=counted_data.values(), bins=range(50))
これにより、hist
を使用してデータを再ビン化できます。
weights
キーワード引数をnp.histgram
(plt.hist
がその下で呼び出す)に使用できます。
val, weight = Zip(*[(k, v) for k,v in counted_data.items()])
plt.hist(val, weights=weight)
onlyがキーとして整数を持っていると仮定すると、bar
を直接使用することもできます。
min_bin = np.min(counted_data.keys())
max_bin = np.max(counted_data.keys())
bins = np.arange(min_bin, max_bin + 1)
vals = np.zeros(max_bin - min_bin + 1)
for k,v in counted_data.items():
vals[k - min_bin] = v
plt.bar(bins, vals, ...)
ここで...は、bar
(doc) に渡したい引数です。
データを再ビン化したい場合は、 頻度を示す個別のリストのあるヒストグラムを参照してください
Seabornを使用してヒストグラムをプロットすることもできます。
import matplotlib.pyplot as plt
import seaborn as sns
sns.distplot(list(counted_data.keys()), hist_kws={"weights":list(counted_data.values())})
「bins」配列の長さは「counts」の長さよりも長くなければなりません。ヒストグラムを完全に再構築する方法は次のとおりです。
import numpy as np
import matplotlib.pyplot as plt
bins = np.array([1, 2, 3, 4, 5, 6, 7, 8, 9]).astype(float)
counts = np.array([5, 3, 4, 5, 6, 1, 3, 7]).astype(float)
centroids = (bins[1:] + bins[:-1]) / 2
counts_, bins_, _ = plt.hist(centroids, bins=len(counts),
weights=counts, range=(min(bins), max(bins)))
plt.show()
assert np.allclose(bins_, bins)
assert np.allclose(counts_, counts)