0

所以我有一個二維數組data,看起來像這樣:Python - 在特定條件下選擇數組的行嗎?

enter image description here

我想指望兩列的一定條件的行數。例如,在陣列的這個特殊的片,我只有

1 | 2 

但考慮到第三排是range(1,4)和第四range(0,3),我可以擁有所有的以下組合:

1 | 0 
1 | 1 
1 | 2 

2 | 0 
2 | 1 
2 | 2 

3 | 0 
3 | 1 
3 | 2 

我想要選擇那些條件爲真的每個的行。但我不知道該怎麼辦?在過去的2個小時裏,我一直在研究這個問題,並且提出了使用for循環,列表解析等等的東西。但是它變得越來越複雜,而且沒有任何一種方法可以實際工作。有沒有一種好方法可以在numpy中做到這一點,甚至只是普通的Python?

任何幫助將不勝感激,謝謝!

回答

1

這工作:

import numpy as np 
# data array 
data = np.array([[4,3,1,2],[4,3,5,1],[1,2,1,0]]) 
# array of acceptable combinations 
cond = np.array([[1,0],[1,2]]) 
# index of rows matching the conditions 
idx=np.array([any(np.equal(cond,row).all(1)) for row in data[:,2:]]) 
# selected rows 
data[idx] 
# array([[4, 3, 1, 2], 
# [1, 2, 1, 0]] 
+1

哦......我不會這樣想。顯然我需要學習更多的numpy!非常感謝你解釋得很好:) – ocean800

+0

hmmm我嘗試了不同的東西,並使用了'cond = np.array([[1,0]])'因爲我需要這個條件來得到'1 | 0'的情況。然而,在這個例子中,像這樣的條件只返回比第二個'0'大的東西。有什麼方法可以改變它嗎? – ocean800

+1

你是對的,它不工作,因爲如何編寫__contains__。我編輯了答案,它應該適用於一般情況。 – Mahdi

2

布爾掩蔽了良好的通用工具,用於基於一個或多個條件的陣列中選擇的行或列(或多個元件)。

使與整數的數組在[0,9)範圍:

In [326]: arr=np.random.randint(0,10,(20,4)) 
In [327]: arr 
Out[327]: 
array([[9, 4, 1, 1], 
     [6, 1, 9, 6], 
     [5, 3, 4, 9], 
     [7, 4, 0, 4], 
     [6, 2, 3, 5], 
     [4, 5, 1, 8], 
     [0, 9, 1, 3], 
     [7, 7, 1, 5], 
     [5, 9, 6, 6], 
     [0, 9, 2, 1], 
     [4, 9, 1, 6], 
     [5, 1, 5, 2], 
     [1, 5, 2, 0], 
     [9, 0, 6, 5], 
     [1, 9, 2, 4], 
     [6, 7, 7, 9], 
     [5, 2, 5, 4], 
     [1, 6, 5, 9], 
     [0, 4, 3, 1], 
     [7, 7, 7, 7]]) 

查找2列中的元素0和3之間Python允許測試象0<x<3,但numpy只允許一個雙面的。括號對於建立操作員順序非常重要。 (|爲或):

In [328]: mask=(0<arr[:,2:]) & (arr[:,2:]<3) 
In [329]: mask 
Out[329]: 
array([[ True, True], 
     [False, False], 
     [False, False], 
     [False, False], 
     [False, False], 
     [ True, False], 
     [ True, False], 
     [ True, False], 
     [False, False], 
     [ True, True], 
     [ True, False], 
     [False, True], 
     [ True, False], 
     [False, False], 
     [ True, False], 
     [False, False], 
     [False, False], 
     [False, False], 
     [False, True], 
     [False, False]], dtype=bool) 

現在,我們可以選擇行,其中任一列是在正確的範圍內:

In [330]: arr[mask.any(axis=1),:] 
Out[330]: 
array([[9, 4, 1, 1], 
     [4, 5, 1, 8], 
     [0, 9, 1, 3], 
     [7, 7, 1, 5], 
     [0, 9, 2, 1], 
     [4, 9, 1, 6], 
     [5, 1, 5, 2], 
     [1, 5, 2, 0], 
     [1, 9, 2, 4], 
     [0, 4, 3, 1]]) 

或其中兩個是:

In [331]: arr[mask.all(axis=1),:] 
Out[331]: 
array([[9, 4, 1, 1], 
     [0, 9, 2, 1]]) 

where通常用於將布爾數組轉換爲索引號:

In [332]: np.where(mask.all(axis=1)) 
Out[332]: (array([0, 9], dtype=int32),) 
In [333]: arr[_,:] 
Out[333]: 
array([[[9, 4, 1, 1], 
     [0, 9, 2, 1]]])