2017-08-09 98 views
3

我想根據需要全部滿足的條件列表來選擇DataFrame的行。 這些條件存儲在字典中,格式爲{column:max-value}。Pandas DataFrame:如何在多個條件下選擇行?

這是一個例子:dict = {'name': 4.0, 'sex': 0.0, 'city': 2, 'age': 3.0}

我需要選擇所有數據幀行,其中相應的屬性是小於或等於在字典中的相應值。

我知道,選擇基於兩個或兩個以上條件的行我可以寫:

rows = df[(df[column1] <= dict[column1]) & (df[column2] <= dict[column2])] 

我的問題是,我怎麼能選擇行存在於一個Python化的方式字典的條件相匹配? 我試過這種方式,

keys = dict.keys() 
rows = df[(df[kk] <= dict[kk]) for kk in keys] 

,但它給我一個錯誤=「[ expected」不會消失,甚至把[符號。

+2

因爲'dict'是一個內置的Python字典的構造函數不要對你的變量'dict'。 – Abdou

回答

2

我們可以使用DataFrame.query()方法是這樣的:

In [109]: dct = {'name': 4.0, 'sex': 0.0, 'city': 2, 'age': 3.0} 

In [110]: qry = ' and '.join(['{} <= {}'.format(k,v) for k,v in dct.items()]) 

In [111]: qry 
Out[111]: 'name <= 4.0 and sex <= 0.0 and city <= 2 and age <= 3.0' 

In [112]: df.query(qry) 
... 
2

你可以利用熊貓自動光軸對齊。考慮到與['age', 'city', 'name', 'sex']列的數據幀,並用相同的指數系列,您可以使用

In [29]: df < pd.Series(dct) 
Out[29]: 
     age city name sex 
0 False False False False 
1 False False False False 
2 True False False False 
3 False True False False 
4 True True True False 
... 

然後你就可以找到它們的行比較反對在系列中的相應值的數據幀中的每個條目都True使用

mask = (df <= pd.Series(dct)).all(axis=1) 

並選擇那些與df.loc[mask, :]行。例如,

import numpy as np 
import pandas as pd 
np.random.seed(2017) 
N = 300 
df = pd.DataFrame({'name':np.random.randint(10, size=N), 
        'sex':np.random.randint(2, size=N), 
        'city':np.random.randint(10, size=N), 
        'age':np.random.randint(10, size=N)}) 
dct = {'name': 4.0, 'sex': 0.0, 'city': 2, 'age': 3.0} 

mask = (df <= pd.Series(dct)).all(axis=1) 
print(df.loc[mask, :]) 

產生

 age city name sex 
7  3  2  0 0 
10  1  2  4 0 
150 1  2  4 0 
188 2  2  2 0 
198 3  2  3 0 
229 1  2  0 0 
254 1  2  2 0 
275 3  2  1 0 
276 0  1  4 0 
299 3  1  2 0 
0

你還可以嘗試:

import pandas as pd 
import numpy as np 


N = 300 

df = pd.DataFrame({'name':np.random.randint(10, size=N), 
        'sex':np.random.randint(2, size=N), 
        'city':np.random.randint(10, size=N), 
        'age':np.random.randint(10, size=N)}) 

dct = {'name': 4.0, 'sex': 0.0, 'city': 2, 'age': 3.0} 

df.loc[np.prod([df[k] <= v for k,v in dct.items()],axis=0).astype(bool),:] 

#  age city name sex 
# 7  3  2  0 0 
# 10  1  2  4 0 
# 150 1  2  4 0 
# 188 2  2  2 0 
# 198 3  2  3 0 
# 229 1  2  0 0 
# 254 1  2  2 0 
# 275 3  2  1 0 
# 276 0  1  4 0 
# 299 3  1  2 0 
相關問題