Numpy: 多次元ブールマスクを使用したブロードキャストエラー

作成日 2019年04月03日  ·  3コメント  ·  ソース: numpy/numpy

形状[N、M]の2D配列を2つの1Dブールマスク(形状NおよびM)でインデックス付けしようとすると、TrueとFalseの特定の組み合わせにより、ブロードキャストエラーが発生します(特に1つがすべてFalseの場合)。 この動作が予想されるかどうかはわかりませんが、非常に驚​​くべきことであり、望ましくないようです。

以下の例では、 x[[False, True, True], [True, True, True]]エラーが発生しますが、 x[[False, True, True], True]x[[False, True, True]]は期待どおりの動作をします。

コード例の再現:

import numpy as np
from itertools import product

x = np.zeros((3,3))
mask_1d = [*product([True, False], repeat=3)]

for row_mask, col_mask in product(mask_1d, mask_1d):
    try:
        x[row_mask, col_mask]
    except IndexError as e:
        print(row_mask, col_mask)
        print(e)

エラーメッセージ:

     (True, True, True) (True, True, False)
shape mismatch: indexing arrays could not be broadcast together with shapes (3,) (2,) 
(True, True, True) (True, False, True)
shape mismatch: indexing arrays could not be broadcast together with shapes (3,) (2,) 
(True, True, True) (False, True, True)
shape mismatch: indexing arrays could not be broadcast together with shapes (3,) (2,) 
(True, True, True) (False, False, False)
shape mismatch: indexing arrays could not be broadcast together with shapes (3,) (0,) 
(True, True, False) (True, True, True)
shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (3,) 
(True, True, False) (False, False, False)
shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (0,) 
(True, False, True) (True, True, True)
shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (3,) 
(True, False, True) (False, False, False)
shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (0,) 
(False, True, True) (True, True, True)
shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (3,) 
(False, True, True) (False, False, False)
shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (0,) 
(False, False, False) (True, True, True)
shape mismatch: indexing arrays could not be broadcast together with shapes (0,) (3,) 
(False, False, False) (True, True, False)
shape mismatch: indexing arrays could not be broadcast together with shapes (0,) (2,) 
(False, False, False) (True, False, True)
shape mismatch: indexing arrays could not be broadcast together with shapes (0,) (2,) 
(False, False, False) (False, True, True)
shape mismatch: indexing arrays could not be broadcast together with shapes (0,) (2,)

Numpy / Pythonのバージョン情報:

1.16.2 3.6.8 |Anaconda, Inc.| (default, Dec 30 2018, 01:22:34) 
[GCC 7.3.0]

最も参考になるコメント

ブール配列の場合、コードは、単一の次元またはすべての要素のいずれかに同時にインデックスを付けようとしていることを前提としています。残念ながら、単一のTrueを削除できるように選択が推測されています。 つまり、 row_mask, col_maskを(2,3)ブール配列に変換し、(3,3)配列にインデックスを付けることができないことを検出します。

問題の一部は、タプルとリストが同等として扱われることです。これは、私たちが回避しようとしていることです。 最終的には、マスクが二重リストであることを確認することにより、ブール配列インデックスを処理します。

ただし、今のところ、唯一の解決策はx[row_mask][:, col_mask]を実行することだと思います。

cc @ eric-wieserは、インデックス作成操作の「タプルをリストとして扱う」の非推奨に取り組んできました。

ps最も迷惑な私はこの違いを見つけます:

x = np.arange(9).reshape(3, 3)
# x[[False, True, True], True]
# array([[3, 4, 5],
#        [6, 7, 8]])
x[[False, True, True], False]
# IndexError: shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (0,) 

全てのコメント3件

ブール配列の場合、コードは、単一の次元またはすべての要素のいずれかに同時にインデックスを付けようとしていることを前提としています。残念ながら、単一のTrueを削除できるように選択が推測されています。 つまり、 row_mask, col_maskを(2,3)ブール配列に変換し、(3,3)配列にインデックスを付けることができないことを検出します。

問題の一部は、タプルとリストが同等として扱われることです。これは、私たちが回避しようとしていることです。 最終的には、マスクが二重リストであることを確認することにより、ブール配列インデックスを処理します。

ただし、今のところ、唯一の解決策はx[row_mask][:, col_mask]を実行することだと思います。

cc @ eric-wieserは、インデックス作成操作の「タプルをリストとして扱う」の非推奨に取り組んできました。

ps最も迷惑な私はこの違いを見つけます:

x = np.arange(9).reshape(3, 3)
# x[[False, True, True], True]
# array([[3, 4, 5],
#        [6, 7, 8]])
x[[False, True, True], False]
# IndexError: shape mismatch: indexing arrays could not be broadcast together with shapes (2,) (0,) 

はい、 x[row_mask][:, col_mask]は私がやったことです。 説明ありがとうございます、調査されてうれしいです。

arr[np.ix_(index)]は、ここで、またはNEP 21のように外部インデックスロジックの外部の言葉であなたが望んでいる/期待しているものだと思います: https

多分それはいつか取り上げられるでしょう。 NEPはまた、少なくとも現在のインデックス作成では、複数のブールインデックスを非推奨にする必要があると述べています(この特定のユースケースを許可するかどうかはまだ争われている可能性があります。一貫性がありますが、ユースケースが少なく、かなり混乱する可能性があります。いずれの場合も)。

このページは役に立ちましたか?
0 / 5 - 0 評価