Python – ML/DLのmodel開発でよく使うNumPy
今回はJupyter notebookでmodelingする際に、個人的によく使うnumpy関連の関数を備忘も兼ねてまとめてみました。
numpy.arange()
numpy.arange() は連番または等差数列を生成する関数です。使い方は Python 本体の組み込み関数range()とほぼ同様です。
numpy.arange([start,] stop [,step], dtype=None)
numpy.arange(n) は 0 から n-1 の数字が並ぶ配列を返します。
In [1]: import numpy as np
In [2]: np.arange(10)
Out[2]: array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9])
numpy.arange(m, n) は m から n-1 の連番配列を返します。
In [3]: np.arange(5, 9)
Out[3]: array([5, 6, 7, 8])
第3引数 step は数字同士の間隔です。numpy.arange(m, n, s) は m から始まって s 間隔で n-1 までの等差数列を生成します。
In [4]: np.arange(1, 10, 2)
Out[4]: array([1, 3, 5, 7, 9])
オプション引数 dtype には要素のデータ型を渡します(省略すると入力値から類推して自動的にデータ型が決定されます)。
In [5]: np.arange(10, dtype=float)
Out[5]: array([0., 1., 2., 3., 4., 5., 6., 7., 8., 9.])
reshape関数を使用すると、連続数字の二次元配列を生成することができます。
In [6]: np.arange(1, 10).reshape(3, 3)
Out[6]:
array([[1, 2, 3],
[4, 5, 6],
[7, 8, 9]])
numpy.zeros()
numpy.zeros() は 0 で埋め尽くされた配列を生成します。
numpy.zeros(shape, dtype=None, order="C")
numpy.zeros(9) は 9 個の 0.0 が並ぶ配列を生成します。
In [7]: np.zeros(9)
Out[7]: array([0., 0., 0., 0., 0., 0., 0., 0., 0.])
デフォルトでは要素のデータ型はfloat型となります。データ型はdtypeで指定することができます。
In [8]: np.zeros(9, dtype=int)
Out[8]: array([0, 0, 0, 0, 0, 0, 0, 0, 0])
shape にタプルを渡すと、配列の形が指定できます。
In [9]: np.zeros((3, 3), dtype=int)
Out[9]:
array([[0, 0, 0],
[0, 0, 0],
[0, 0, 0]])
numpy.zeros_like()
numpy.zeros_like() は与えられた引数と同じ形状の 0 で埋め尽くされた配列を生成します。
numpy.zeros_like(a, dtype=None, order='K', subok=True, shape=None)
a に 2 × 3 配列を渡すと、0 で埋め尽くされた 2 × 3 配列が生成されます。
In [11]: arr = np.array([[1, 2, 3], [4, 5, 6]])
...: arr
Out[11]:
array([[1, 2, 3],
[4, 5, 6]])
In [12]: np.zeros_like(arr)
Out[12]:
array([[0, 0, 0],
[0, 0, 0]])
numpy.ones()
numpy.ones() は 1 で埋め尽くされた配列を生成します。
numpy.ones(shape, dtype=None, order="C")
numpy.ones(9) は 9 個の 1 が並ぶ配列を生成します。データ型は dtype で指定します (デフォルトは float)。
In [13]: np.ones(9, dtype=int)
Out[13]: array([1, 1, 1, 1, 1, 1, 1, 1, 1])
shape にタプルを渡して配列の形を指定することができます。
In [14]: np.ones((3, 3), dtype=int)
Out[14]:
array([[1, 1, 1],
[1, 1, 1],
[1, 1, 1]])
numpy.ones_like()
numpy.ones_like() は与えられた引数と同じ形状で全ての要素を 1 とした配列を生成します。
numpy.ones_like(a, dtype=None, order='K', subok=True, shape=None)
a に 2 × 4 の配列を渡すと、1 で埋め尽くされた 2 × 4 の配列が生成されます。
In [15]: arr = np.array([[1, 2, 3, 4], [5, 6, 7, 8]])
...: arr
Out[15]:
array([[1, 2, 3, 4],
[5, 6, 7, 8]])
In [16]: np.ones_like(arr)
Out[16]:
array([[1, 1, 1, 1],
[1, 1, 1, 1]])
numpy.full()
numpy.full() は同じ要素で埋め尽くされた配列を生成します。
numpy.full(shape, fill_value, dtype=None, order='C')
全ての要素が 5 である 2 × 3 の配列を作りたいときには、shape に (2, 3), fill_value に 5 を渡します。
In [17]: np.full((2, 3), 5, dtype="int32")
Out[17]:
array([[5, 5, 5],
[5, 5, 5]], dtype=int32)
numpy.full_like()
numpy.full_like() は受け取った配列 a と同じ形状をもつ、指定要素 (fill_value) で埋め尽くされた配列を返します。
numpy.full_like(a, fill_value, dtype=None, order='K', subok=True, shape=None)
In [18]: arr = np.array([[1, 2, 3, 4], [5, 6, 7, 8]])
...: arr
Out[18]:
array([[1, 2, 3, 4],
[5, 6, 7, 8]])
In [19]: np.full_like(arr, 9)
Out[19]:
array([[9, 9, 9, 9],
[9, 9, 9, 9]])
numpy.eye()
numpy.eye() は対角線上に 1 が並ぶ配列を生成します。
numpy.eye(N, M=None, k=0, dtype=None, order='C')
3 × 3 の単位配列を作りたいときには引数 N に 3 を渡します。
In [20]: np.eye(3, dtype="int32")
Out[20]:
array([[1, 0, 0],
[0, 1, 0],
[0, 0, 1]], dtype=int32)
引数 M には配列の列数を指定します(省略すると M = N です)。引数 k には対角線左上隅の 1 の位置を渡します。列(右)方向にずらす場合は正の値を、行(下)方向にずらす場合は負の値を指定します。
In [21]: np.eye(3, 4, k=1, dtype="int32")
Out[21]:
array([[0, 1, 0, 0],
[0, 0, 1, 0],
[0, 0, 0, 1]], dtype=int32)
numpy.identity()
numpy.identity() は主対角成分に 1 が並ぶ正方配列(単位配列)を生成します。
np.identity(n, dtype=None)
第1引数で配列のサイズを指定します。3×3 の単位配列を生成するときは次のようなコードを記述します。
In [23]: np.identity(3, dtype=int)
Out[23]:
array([[1, 0, 0],
[0, 1, 0],
[0, 0, 1]])
numpy.matrix()
numpy.matrix() は文字列から配列を生成する関数です。
numpy.matrix(data, dtype=None, copy=True)
この関数で配列を生成するときは、各行を “;” で区切って指定します。
In [24]: np.matrix("1 2 3 ; 4 5 6 ; 7 8 9")
Out[24]:
matrix([[1, 2, 3],
[4, 5, 6],
[7, 8, 9]])
各要素のデータ型は dtype で指定します。データ型は複素数(complex)です。
In [25]: np.matrix("1 2 3 ; 4 5 6", dtype="complex")
Out[25]:
matrix([[1.+0.j, 2.+0.j, 3.+0.j],
[4.+0.j, 5.+0.j, 6.+0.j]])
numpy.linspace()
numpy.linspace() は開始値 (start) から終了値 (stop) まで均等間隔に数字を並べます(等差数列を生成します)。
numpy.linspace(start, stop, num=50, endpoint=True, retstep=False, dtype=None)
第 3 引数 num には要素数を指定します (デフォルトは 50)。[10 20 30 40 50] という配列を作る場合は次のようになります。
In [27]: np.linspace(10, 100, 10, dtype=int)
Out[27]: array([ 10, 20, 30, 40, 50, 60, 70, 80, 90, 100])
retstep は配列のあとに公差を表示するか否かのオプションです。デフォルトは False になっているので、表示したいときは True を指定します。
In [28]: np.linspace(10, 20, 3, retstep=True)
Out[28]: (array([10., 15., 20.]), 5.0)
numpy.logspace()
numpy.logspace() は対数スケールで等間隔の配列を生成します。
numpy.logspace(start, stop, num=50, endpoint=True, base=10.0, dtype=None)
endpoint が True であるとき、配列の最初の要素は base ** start, 最後の要素は base ** stop です。要素の個数は num で指定します。たとえば、102 から 104 まで 5 個の要素を対数スケールで等間隔に並べる場合は次のコードを記述します。
In [30]: x = np.logspace(2.0, 4.0, num=5)
...: x
Out[30]:
array([ 100. , 316.22776602, 1000. , 3162.27766017,
10000. ])
In [31]: np.log10(x)
Out[31]: array([2. , 2.5, 3. , 3.5, 4. ])
endpoint を False に設定すると、stop を含まない形で配列を生成します。
In [34]: x = np.logspace(2.0, 4.0, num=5, endpoint=False)
...: x
Out[34]:
array([ 100., 251.18864315, 630.95734448, 1584.89319246, 3981.07170553])
In [35]: np.log10(x)
Out[35]: array([2. , 2.4, 2.8, 3.2, 3.6])
numpy.geomspace()
numpy.geomspace() は等比数列 (geometric progression) を返します。
numpy.geomspace(start, stop, num=50, endpoint=True, dtype=None, axis=0)
start=1, stop=10000, num=5 を指定すると、1 から 10000 まで公比 10 で 5 個の数が並びます。
In [36]: np.geomspace(1, 10000, 5, dtype=np.int64)
Out[36]: array([1, 10, 100, 1000, 10000])
endpoint に False を渡すと、stop で指定した値を含まないように等比数列を生成します。
In [37]: np.geomspace(1, 10000, 4, endpoint=False)
Out[37]: array([1., 10., 100., 1000.])
numpy.diag()
numpy.diag() は対角配列を生成、もしくは配列の対角成分を抜き出す関数です。
numpy.diag(v, k=0)
第1引数 v に 1次元配列を渡すと、渡した配列を右斜めの対角要素とする(それ以外の要素を 0 とする)2次元配列を返します。第2引数 k でオフセットを指定することができます(正ならば列方向、負ならば行方向にずらします)。
In [38]: v = np.array([1, 2, 3])
...: v
Out[38]: array([1, 2, 3])
In [39]: np.diag(v)
Out[39]:
array([[1, 0, 0],
[0, 2, 0],
[0, 0, 3]])
In [40]: np.diag(v, 2)
Out[40]:
array([[0, 0, 1, 0, 0],
[0, 0, 0, 2, 0],
[0, 0, 0, 0, 3],
[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0]])
In [41]: np.diag(v, -2)
Out[41]:
array([[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0],
[1, 0, 0, 0, 0],
[0, 2, 0, 0, 0],
[0, 0, 3, 0, 0]])
第1引数 v に 2次元配列を渡すと、配列から右斜めの対角線に並ぶ要素を抜き出して 1 次元配列として返します。第2引数 k はオフセットです。
In [43]: x = np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
...: x
Out[43]:
array([[1, 2, 3],
[4, 5, 6],
[7, 8, 9]])
In [44]: np.diag(x)
Out[44]: array([1, 5, 9])
In [45]: np.diag(x, 1)
Out[45]: array([2, 6])
In [46]: np.diag(x, -1)
Out[46]: array([4, 8])
numpy.fromfunction()
numpy.fromfunction() は、第1引数に渡した関数を使って配列を生成します。
numpy.fromfunction(function, shape, **kwargs)
2変数 i と j の関数を渡すと、2次元配列におけるインデックス (i, j) の要素をその関数にしたがって決定することになります。
In [47]: np.fromfunction(lambda i, j: i + j, (3, 4), dtype=int)
Out[47]:
array([[0, 1, 2, 3],
[1, 2, 3, 4],
[2, 3, 4, 5]])
3変数 i, j, k の関数を渡すと、3次元配列を生成します。
In [48]: np.fromfunction(lambda i, j, k: i * j + k, (2, 3, 4), dtype=int)
Out[48]:
array([[[0, 1, 2, 3],
[0, 1, 2, 3],
[0, 1, 2, 3]],
[[0, 1, 2, 3],
[1, 2, 3, 4],
[2, 3, 4, 5]]])
まとめ
ということで、Python – ML/DLのmodel開発でよく使うNumPyについて記載しました。Jupyter notebookでmodelingするときによく使っているnumpyは他にもあるので、以下の記事もご参考いただければと思います。