1. ホーム
  2. スクリプト・コラム
  3. その他

[解決済み】ValueError: すべての入力配列は同じ次元数でなければならない

2022-01-12 13:08:42

質問

20x361 の行列の最後の列を複製したい。 n_list_converted の場合、以下のようなコードになります。

n_last = []
n_last = n_list_converted[:, -1]
n_lists = np.append(n_list_converted, n_last, axis=1)

でエラーが発生します。 np.append :

ValueError: all the input arrays must have same number of dimensions

以下のコードで行列の次元を確認したところ

 print(n_last.shape, type(n_last), n_list_converted.shape, type(n_list_converted))

というコンソールが表示されます。

(20L,) (20L, 361L)

解決方法は?

3x4の配列から始めて、3x1の配列を軸1に連結すると、3x5の配列が得られます。

In [911]: x = np.arange(12).reshape(3,4)
In [912]: np.concatenate([x,x[:,-1:]], axis=1)
Out[912]: 
array([[ 0,  1,  2,  3,  3],
       [ 4,  5,  6,  7,  7],
       [ 8,  9, 10, 11, 11]])
In [913]: x.shape,x[:,-1:].shape
Out[913]: ((3, 4), (3, 1))

連結する入力はどちらも2次元であることに注意してください。

を省略します。 :x[:,-1] は(3,)の形状であり、1dであるため、エラーとなります。

In [914]: np.concatenate([x,x[:,-1]], axis=1)
...
ValueError: all the input arrays must have same number of dimensions

のコードは np.append は、(軸が指定されているこのケースでは)

return concatenate((arr, values), axis=axis)

そこで、構文を少し変えて append が動作します。リストの代わりに2つの引数を取ります。これはリストを模倣しています。 append は構文ですが、そのリストメソッドと混同しないでください。

In [916]: np.append(x, x[:,-1:], axis=1)
Out[916]: 
array([[ 0,  1,  2,  3,  3],
       [ 4,  5,  6,  7,  7],
       [ 8,  9, 10, 11, 11]])

np.hstack は、すべての入力が atleast_1d そして、連結を行う。

return np.concatenate([np.atleast_1d(a) for a in arrs], 1)

そのため、同じように x[:,-1:] の入力が必要です。基本的に同じ動作です。

np.column_stack も軸 1 の連結を行いますが、まず 1d の入力を次のように通過させます。

array(arr, copy=False, subok=True, ndmin=2).T

これは、その(3,)配列を(3,1)配列にするための一般的な方法です。

In [922]: np.array(x[:,-1], copy=False, subok=True, ndmin=2).T
Out[922]: 
array([[ 3],
       [ 7],
       [11]])
In [923]: np.column_stack([x,x[:,-1]])
Out[923]: 
array([[ 0,  1,  2,  3,  3],
       [ 4,  5,  6,  7,  7],
       [ 8,  9, 10, 11, 11]])

これらすべての「積み重ね」は便利ですが、長い目で見れば、寸法を理解し、ベースとなる np.concatenate . また、このような関数のコードの調べ方も知っておきましょう。私が使っているのは ipython ?? の魔法をよく使います。

また、タイムテストでは np.concatenate このような小さな配列では、関数呼び出しのレイヤーが増えることで大きな時間差が生じます。