次のコードを使用して、numpy-ndarrayを作成します。ファイルには9つの列があります。各列を明示的に入力します。
dataset = np.genfromtxt("data.csv", delimiter=",",dtype=('|S1', float, float,float,float,float,float,float,int))
次に、各列の説明的な統計情報(最小、最大、標準偏差、平均、中央値など)を取得します。これを行う簡単な方法はありませんか?
私はこれを試しました:
from scipy import stats
stats.describe(dataset)
しかし、これはエラーを返します:TypeError: cannot perform reduce with flexible type
私の質問は:作成されたnumpy-ndarrayの記述統計を取得するにはどうすればよいですか。
これはきれいな解決策ではありませんが、仕事を成し遂げます。問題は、複数のdtypeを指定することにより、本質的にタプルの1D配列(実際には_np.void
_)を作成していることです。文字列。
これは、2ラウンドで読み取るか、pandas with _read_csv
_)を使用して解決できます。
numpy
に固執することにした場合:
_import numpy as np
a = np.genfromtxt('sample.txt', delimiter=",",unpack=True,usecols=range(1,9))
s = np.genfromtxt('sample.txt', delimiter=",",unpack=True,usecols=0,dtype='|S1')
from scipy import stats
for arr in a: #do not need the loop at this point, but looks prettier
print(stats.describe(arr))
#Output per print:
DescribeResult(nobs=6, minmax=(0.34999999999999998, 0.70999999999999996), mean=0.54500000000000004, variance=0.016599999999999997, skewness=-0.3049304880932534, kurtosis=-0.9943046886340534)
_
この例では、最終的な配列にはdtype
ではなくfloat
としてint
がありますが、arr.astype(int)
を使用して簡単に(必要に応じて)intに変換できます。
genfromtxt
からの混合データをどのように処理するかという問題が頻繁に発生します。人々は2D配列を期待し、代わりに列ごとにインデックスを作成できない1Dを取得します。それは、各列に異なるdtypeを持つ構造化配列を取得するためです。
genfromtxt
docのすべての例はこれを示しています:
>>> s = StringIO("1,1.3,abcde")
>>> data = np.genfromtxt(s, dtype=[('myint','i8'),('myfloat','f8'),
... ('mystring','S5')], delimiter=",")
>>> data
array((1, 1.3, 'abcde'),
dtype=[('myint', '<i8'), ('myfloat', '<f8'), ('mystring', '|S5')])
しかし、この種のデータにアクセスする方法を説明しましょう
In [361]: txt=b"""A, 1,2,3
...: B,4,5,6
...: """
In [362]: data=np.genfromtxt(txt.splitlines(),delimiter=',',dtype=('S1,int,float,int'))
In [363]: data
Out[363]:
array([(b'A', 1, 2.0, 3), (b'B', 4, 5.0, 6)],
dtype=[('f0', 'S1'), ('f1', '<i4'), ('f2', '<f8'), ('f3', '<i4')])
そのため、私の配列には2つのレコードがあり(形状を確認)、それらはリストにタプルとして表示されます。
fields
には、列番号ではなく名前でアクセスします(構造化配列のドキュメントリンクを追加する必要がありますか?)
In [364]: data['f0']
Out[364]:
array([b'A', b'B'],
dtype='|S1')
In [365]: data['f1']
Out[365]: array([1, 4])
'subarrays'でdtype
を選択すると、このような場合により便利です。これはより高度なdtypeトピックです
In [367]: data=np.genfromtxt(txt.splitlines(),delimiter=',',dtype=('S1,(3)float'))
In [368]: data
Out[368]:
array([(b'A', [1.0, 2.0, 3.0]), (b'B', [4.0, 5.0, 6.0])],
dtype=[('f0', 'S1'), ('f1', '<f8', (3,))])
In [369]: data['f1']
Out[369]:
array([[ 1., 2., 3.],
[ 4., 5., 6.]])
文字列は引き続きS1
としてロードされますが、数値は3列配列になりました。それらはすべてfloat(またはint)であることに注意してください。
In [371]: from scipy import stats
In [372]: stats.describe(data['f1'])
Out[372]: DescribeResult(nobs=2,
minmax=(array([ 1., 2., 3.]), array([ 4., 5., 6.])),
mean=array([ 2.5, 3.5, 4.5]),
variance=array([ 4.5, 4.5, 4.5]),
skewness=array([ 0., 0., 0.]),
kurtosis=array([-2., -2., -2.]))