2017-08-29 71 views
2

我想過濾掉包含數據框中多列的特定值的行。篩選包含列中某些值的行

E.g

code tag number floor note 
1 1111 * **  34  no 
2 2323 7 899  7  no 
3 3677 # 900 11  no 
4 9897 10 134 *  no 
5 # # 566 11  no 
6 3677 55 908 11  no 

我想篩選出所有行包含#,*,**列碼,標籤,編號,樓層。

我想什麼是

code tag number floor note 
1 1111 * **  34  no 
3 3677 # 900 11  no 
4 9897 10 134 *  no 
5 # # 566 11  no 

我試圖用ISIN方法在數據幀,但它確實有一列工作,但在多列不起作用。謝謝!

回答

1

選項1
假設沒有其他已存在的pir

df[df.replace(['#', '*', '**'], 'pir').eq('pir').any(1)] 

    code tag number floor note 
1 1111 *  ** 34 no 
3 3677 # 900 11 no 
4 9897 10 134  * no 
5  # # 566 11 no 

選項2
令人討厭的numpy broa dcasting。快在第一,但平方縮放

df[(df.values[None, :] == np.array(['*', '**', '#'])[:, None, None]).any(0).any(1)] 

    code tag number floor note 
1 1111 *  ** 34 no 
3 3677 # 900 11 no 
4 9897 10 134  * no 
5  # # 566 11 no 

選項3
較少令人厭惡np.in1d

df[np.in1d(df.values, ['*', '**', '#']).reshape(df.shape).any(1)] 

    code tag number floor note 
1 1111 *  ** 34 no 
3 3677 # 900 11 no 
4 9897 10 134  * no 
5  # # 566 11 no 

選項4
多年來與頂端

df[list(
    map(bool, 
     map({'*', '**', '#'}.intersection, 
      map(set, 
       zip(*(df[c].values.tolist() for c in df))))) 
)] 

    code tag number floor note 
1 1111 *  ** 34 no 
3 3677 # 900 11 no 
4 9897 10 134  * no 
5  # # 566 11 no 
+0

哦,快點。Brb撤消一些投票。 –

1

我想你需要applyisinany布爾索引:

list = ['#','*','**'] 
cols = ['code','tag','number','floor'] 
df[df[cols].apply(lambda x: x.isin(list).any(), axis=1)] 

輸出:

code tag number floor note 
1 1111 *  ** 34 no 
3 3677 # 900 11 no 
4 9897 10 134  * no 
5  # # 566 11 no 
1

您也可以使用df.applymap

s = {'*', '**', '#'} 
df[df.applymap(lambda x: x in s).max(1)] 

    code tag number floor note 
1 1111 *  ** 34 no 
3 3677 # 900 11 no 
4 9897 10 134  * no 
5  # # 566 11 no 

PIR suggested一個瘋狂的(!但它的工作原理)替代:

df[df.apply(set, 1) & {'*', '**', '#'}] 

    code tag number floor note 
1 1111 *  ** 34 no 
3 3677 # 900 11 no 
4 9897 10 134  * no 
5  # # 566 11 no 
+1

@piRSquared因爲它的工作原因而Re然心動。如果你沒有問題,可以添加它作爲答案? –