[英]Numpy: How to check for tuples existence in ndarray
在numpy數組中使用元組時,我發現了一個奇怪的行為。 我想得到一個布爾表,告訴我陣列中a
哪些元組也存在於數組b
。 通常情況下,我會使用任何in
, in1d
。 當tuple(a[1]) == b[1,1]
得到True
,它們都不起作用。
我這樣填寫我的a
和b
:
a = numpy.array([(0,0)(1,1)(2,2)], dtype=tuple)
b = numpy.zeros((3,3), dtype=tuple)
for i in range(0,3):
for j in range(0,3):
b[i,j] = (i,j)
任何人都可以告訴我解決我的問題,請告訴我為什么這不能按預期工作?
(在這里使用python2.7和numpy1.6.2順便說一下。)
為什么這不起作用
簡短的版本是numpy的array.__contains__()
似乎被打破了。 python中的in
運算符在后台調用__contains__()
。
意味着a in b
等於b.__contains__(a)
。
我已經在REPL中加載了你的數組並嘗試以下方法:
>>> b[:,0]
array([(0, 0), (1, 0), (2, 0)], dtype=object)
>>> (0,0) in b[:,0] # we expect it to be true
False
>>> (0,0) in list(b[:,0]) # this shouldn't be different from the above but it is
True
>>>
如何解決它
我沒有看到你的列表理解是如何工作的,因為a[x]
是一個元組而b[:,:]
是一個2D矩陣,所以當然它們並不相等。 但我假設你想用in
,而不是==
。 如果我在這里錯了,請糾正我,你的意思是我不會看到的不同之處。
第一步是將b
從2D數組轉換為1D數組,這樣我們就可以線性地篩選它並將其轉換為列表以避免numpy的破壞array.__contains()
如下所示:
bb = list(b.reshape(b.size))
或者,更好的是,使它成為一個set
因為元組是不可變的並且in
集合中檢in
是O(1)而不是列表的O(n)行為
>>> bb = set(b.reshape(b.size))
>>> print bb
set([(0, 1), (1, 2), (0, 0), (2, 1), (1, 1), (2, 0), (2, 2), (1, 0), (0, 2)])
>>>
接下來,我們只使用列表推導來推導布爾表
>>> truth_table = [tuple(aa) in bb for aa in a]
>>> print truth_table
[True, True, True]
>>>
完整代碼:
def contained(a,b):
bb = set(b.flatten())
return [tuple(aa) in bb for aa in a]
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.