NumPyに実装されている関数には、配列を生成するための様々な関数が存在します。その中でもnp.empty関数は、値の初期化を行うことなく配列を生成するものです。

本記事では、NumPyのempty関数の使い方を解説します。

np.empty

配列の生成速度が若干高速になることがあるため、値を0や1で初期化する必要のない場合は、np.emptyを使いましょう。

np.emptyのAPIドキュメントは以下の通りです。

np.empty(shape, dtype=float, order=’C’)

params:

パラメータ名 概要
shape int
または
intのタプル
生成する配列の形状(shape)を指定します。
dtype dtype 省略可能(初期値float)
生成される配列の要素のデータ型(dtype)を指定します。
order CまたはF 省略可能(初期値’C’)
配列のデータの保存の仕方を指定します。

returns:

指定されたshapeを持つ、値が初期化されていない配列(ndarray)が返されます。

np.emptyの引数には、第一引数に生成したい配列の形状(shape)を、第二引数にデータ型(dtype)を、そして最後に配列のデータの保存の仕方を指定します。最後の引数は、Fortranのような順序を指定する場合に使われるもので、あまり使用されません。

実際のコードで使い方を見ていきましょう。

In [1]: import numpy as np

In [2]: np.empty(10) # 値を初期化しない1次元配列
Out[2]:
array([ -0.00000000e+000,  -1.49457395e-154,   2.26371905e-314,
         2.26388775e-314,   2.26388851e-314,   2.26388892e-314,
         2.25992832e-314,   0.00000000e+000,   2.24756287e-314,
         7.08067556e-309])

In [3]: np.empty((2, 3)) # 2×3の2次元配列。
Out[3]:
array([[ -0.00000000e+000,   1.29073925e-231,   2.24578104e-314],
       [  2.24578779e-314,  -0.00000000e+000,  -0.00000000e+000]])

次にデータ型を指定していきます。

In [5]: np.empty(5, dtype = np.int8) # dtypeをint8に指定。
Out[5]: array([0, 0, 0, 0, 0], dtype=int8)

In [6]: np.empty(10, dtype = bool) # bool値にすることもできる。
Out[6]: array([False, False, False, False, False, False, False, False, False, False], dtype=bool)

In [7]: np.empty(10, dtype= complex) # 複素数でも生成可能。
Out[7]:
array([ -0.00000000e+000 +1.49457395e-154j,
         2.24484205e-314 +1.48219694e-323j,
         0.00000000e+000 +0.00000000e+000j,
         0.00000000e+000 +1.66093094e-216j,
         2.24652642e-314 +2.26209998e-314j,
         3.92523161e-257 +0.00000000e+000j,
         0.00000000e+000 +1.90024900e+284j,
         0.00000000e+000 +0.00000000e+000j,
         1.49457395e-154 +0.00000000e+000j,
         0.00000000e+000 +2.68678533e+154j])

他の生成関数との比較

今回は比較対象として要素が0の配列を生成するnp.zerosと要素が1の配列を生成するnp.onesを用います。np.zerosについての詳細は以下のページで解説しています。

0を要素とする配列を生成するnumpy.zerosの使い方 /features/numpy-zeros.html

では、実行速度の比較をしてみます。

  In [15]: %timeit np.zeros(10000)
4.94 µs ± 105 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)

In [16]: %timeit np.empty(10000)
1.34 µs ± 14 ns per loop (mean ± std. dev. of 7 runs, 1000000 loops each)

In [17]: %timeit np.ones(10000)
8.6 µs ± 84.1 ns per loop (mean ± std. dev. of 7 runs, 100000 loops each)

emptyの方が、3~4倍程度速いことがわかりますね。np.onesとの比較では6倍程度の違いがあります。

実行速度が高速なだけでなく、明示的に初期化する必要がないということを他の人がコードを読んだときに理解してもらうためにも、値を初期化する必要がないときはnp.emptyを使うことをおすすめします。