2017-05-29 95 views
0

我有以下的解释:筛选器列表的字典在Python

dict = {'Sex':['Male','Male','Female','Female','Male'], 
     'Height': [100,200,150,80,90], 
     'Weight': [20,60,40,30,30]} 

我希望能够过滤使用条件字典上的一个键。例如,如果我想继续只限男性:

new_dict = {'Sex':['Male','Male','Male'], 
      'Height': [100,200,90], 
      'Weight': [20,60,30]} 
+1

将其转换成数据库。 –

+1

谢谢但我的配置不理想。 – user2475110

+0

你想成为多么灵活?可以举另一个例子为“height> 100”吗? –

回答

4

您可以使用字典理解和相应的指数,在检查项目在关键'Sex'在构建值列表:

d = {k: [x for i, x in enumerate(v) if dct['Sex'][i]=='Male'] 
             for k, v in dct.items()} 
print(d) 
# {'Sex': ['Male', 'Male', 'Male'], 
# 'Weight': [20, 60, 30], 
# 'Height': [100, 200, 90]} 
3

,而不是试图跟踪指数的,“转”的数据结构是一个字典列表:

data = [{'Sex': 'Male', 'Height': 100, 'Weight': 20}, 
     {'Sex': 'Male', 'Height': 200, 'Weight': 60}, 
     {'Sex': 'Female', 'Height': 150, 'Weight': 40}, 
     {'Sex': 'Female', 'Height': 80, 'Weight': 30}, 
     {'Sex': 'Male', 'Height': 90, 'Weight': 30}] 

only_males = [person for person in data if person['Sex'] == 'Male'] 
only_males 
# [{'Sex': 'Male', 'Height': 100, 'Weight': 20}, 
# {'Sex': 'Male', 'Height': 200, 'Weight': 60}, 
# {'Sex': 'Male', 'Height': 90, 'Weight': 30}] 
+0

因此,您应该展示OP如何将数据转置为假设它可能很大。你的是最好的选择国际海事组织只使用字典 – JBernardo

+0

我的猜测是数据采用了DeepSpace建议的格式,而OP则向他们申请了一些他向我们显示的格式。 – gboffi

0

你可以使用itertools.compress和字典解析:

>>> import itertools 

>>> dct = {'Sex': ['Male', 'Male', 'Female', 'Female', 'Male'], 
...  'Height': [100, 200, 150, 80, 90], 
...  'Weight': [20, 60, 40, 30, 30]} 

>>> mask = [item == 'Male' for item in dct['Sex']] 

>>> new_dict = {key: list(itertools.compress(dct[key], mask)) for key in dct} 
>>> new_dict 
{'Height': [100, 200, 90], 
'Sex': ['Male', 'Male', 'Male'], 
'Weight': [20, 60, 30]} 
0

可以使用大熊猫数据框(install包第一)

>>> data = pandas.DataFrame(
    {'Sex':['Male','Male','Female','Female','Male'], 
    'Height': [100,200,150,80,90], 
    'Weight': [20,60,40,30,30]} 
) 

>>> data[data['Sex'] == 'Male'] 
    Height Sex Weight 
0  100 Male  20 
1  200 Male  60 
4  90 Male  30 

这会更像一个数据库,并可以过滤了很多东西毫不费力。

1

使用该解决方案collections.defaultdictzip()功能:

d = { 
    'Sex':['Male','Male','Female','Female','Male'], 
    'Height': [100,200,150,80,90], 
    'Weight': [20,60,40,30,30] 
} 

result = collections.defaultdict(list) 
for s,h,w in zip(d['Sex'], d['Height'], d['Weight']): 
    if s == 'Male': 
     result['Sex'].append(s) 
     result['Height'].append(h) 
     result['Weight'].append(w) 

print(dict(result)) 

输出:

{'Sex': ['Male', 'Male', 'Male'], 'Weight': [20, 60, 30], 'Height': [100, 200, 90]} 
0

就个人而言,我会使用对象的列表,而不是,有在同一个对象的相关属性,这方式:

people = [{"Sex": "Male", "Height": 100, "Weight": 20}, {...}, ...] 

我会转换为一个列表这样(assumin克名单在你的字典都具有相同的尺寸):

list = [] 
for i in range(len(dict["Sex"])): 
    list.append({k: v[i] for k, v in dict.iteritems()}) 

或者使用d.items(),如果你是在Python 3.x的

然后你就可以通过键值,更多的细节here

0

容易过滤列表我只是把这个在这里,因为我写的也无妨。它会根据您的字典在内存中创建一个数据库,然后您可以根据您的需要进行查询(灵活地按照您的注意事项)以获得您想要的结果。

dict_ = {'Sex': ['Male', 'Male', 'Female', 'Female', 'Male'], 
     'Height': [100, 200, 150, 80, 90], 
     'Weight': [20, 60, 40, 30, 30]} 

import sqlite3 

conn = sqlite3.connect(':memory:') 
curs = conn.cursor() 
column_headers = [x for x in dict_] # the keys are the headers 
column_types = ('' for x in dict_) 
header_creation = ', '.join([' '.join(x) for x in zip(column_headers, column_types)]) 
curs.execute("CREATE TABLE temp ({})".format(header_creation)) 
bindings = ','.join('?' * (header_creation.count(',') + 1)) 
result_insertion = "INSERT INTO temp ({}) VALUES ({})".format(', '.join(column_headers), bindings) 
for i, item in enumerate(dict_[column_headers[0]]): 
    values = [item] 
    for j in column_headers[1:]: 
     values.append(dict_[j][i]) 
    curs.execute(result_insertion, values) 
conn.commit() 

condition = 'weight >= 40' 

out = curs.execute('SELECT * FROM temp{}'.format(' WHERE {}'.format(condition) if condition else ';')).fetchall() 
dict_out = {} 
for i, k in enumerate(column_headers): 
    dict_out[k] = [x[i] for x in out] 
print(dict_out) # {'Sex': ['Male', 'Female'], 'Weight': [60, 40], 'Height': [200, 150]}