Python中数据帧列中的字典

2024-05-15 01:32:15 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在读取一个csv文件,其中一列包含一个多键目录。以下是一个示例:

import pandas as pd
df = pd.DataFrame({'a':[1,2,3], 'b':[{'AUS': {'arv': '10:00', 'vol': 5}, 'DAL': {'arv': '9:00', 'vol': 1}}, {'DAL': {'arv': '10:00', 'vol': 6}, 'NYU': {'arv': '10:00', 'vol': 3}}, {'DAL': {'arv': '8:00', 'vol': 6}, 'DAL': {'arv': '10:00', 'vol': 1}, 'GBD': {'arv': '12:00', 'vol': 1}}]})

我试图做的是对上述数据帧的b列执行查询,并返回如下所示的相应值。然而,我试图看看是否有一种更直观、更有效的方法可以在大型数据集中执行类似的操作,而不必在dict中循环

#convert column b of df to a dict
df_dict = df.b.to_dict()
print(df_dict)
{0: {'AUS': {'arv': '10:00', 'vol': 5}, 'DAL': {'arv': '9:00', 'vol': 1}}, 1: {'DAL': {'arv': '10:00', 'vol': 6}, 'NYU': {'arv': '10:00', 'vol': 3}}, 2: {'DAL': {'arv': '10:00', 'vol': 1}, 'GBD': {'arv': '12:00', 'vol': 1}}}

def get_value(my_str, my_time):
    total = 0
    for key in df_dict:
        if my_str in df_dict[key].keys():
            if df_dict[key].get(my_str).get('arv') == my_time:
                total = total + df_dict[key].get(my_str).get('vol')
    return total

print("total vol is at 10:00 is: ", get_value('DAL', '10:00'))
total vol is at 10:00 is:  7

Tags: keydfgetismydicttotalarv
2条回答

我建议您在DataFrame中重新组织数据表示:

>>> from collections import defaultdict, Counter
>>> import pandas as pd
>>> input_data = {0: {"AUS": {"arv": "10:00", "vol": 5}, "DAL": {"arv": "9:00", "vol": 1}}, 1: {"DAL": {"arv": "10:00", "vol": 6}, "NYU": {"arv": "10:00", "vol": 3}}, 2: {"DAL": {"arv": "10:00", "vol": 1}, "GBD": {"arv": "12:00", "vol": 1}}}
>>> data = defaultdict(Counter)
>>> for value in input_data.values():
...     for name in value:
...         data[value[name]["arv"]][name] = value[name]["vol"]
... 
>>> data
defaultdict(<class "collections.Counter">, {"10:00": Counter({"DAL": 7, "AUS": 5, "NYU": 3}), "9:00": Counter({"DAL": 1}), "12:00": Counter({"GBD": 1})})
>>> frame = pd.DataFrame(data).T
>>> frame
       AUS  DAL  NYU  GBD
10:00  5.0  7.0  3.0  NaN
9:00   NaN  1.0  NaN  NaN
12:00  NaN  NaN  NaN  1.0
>>> frame[frame.index == "10:00"]["DAL"]
10:00    7.0
Name: DAL, dtype: float64

虽然dukkee的答案是可行的,但我相信如果你想用其他方式操纵数据帧,他的组织有点违反直觉。我还将重新组织数据帧,但方式如下:

input_data = {
    'a':[1,2,3], 
    'b':[{'AUS': {'arv': '10:00', 'vol': 5},
         'DAL': {'arv': '9:00', 'vol': 1}
        },
        {'DAL': {'arv': '10:00', 'vol': 6},
         'NYU': {'arv': '10:00', 'vol': 3}
        },
        {'DAL': {'arv': '8:00', 'vol': 6},
         'DAL': {'arv': '10:00', 'vol': 1},
         'GBD': {'arv': '12:00', 'vol': 1}
        }]
}

data_list = [[input_data['a'][i], key, value['arv'], value['vol']]
            for i, dic in enumerate(input_data['b'])
            for key, value in dic.items()]
df = pd.DataFrame(data_list, columns=['a', 'abr', 'arv', 'vol'])

其结果是:

>>> df
   a  abr    arv  vol
0  1  AUS  10:00    5
1  1  DAL   9:00    1
2  2  DAL  10:00    6
3  2  NYU  10:00    3
4  3  DAL  10:00    1
5  3  GBD  12:00    1

我相信这就是你组织数据的方式。将字典作为数据框中的值对我来说似乎是违反直觉的。通过这种方式,您可以使用loc来解决您的问题:

>>> df.loc[(df['arv']=='10:00') & (df['abr']=='DAL')]
   a  abr    arv  vol
2  2  DAL  10:00    6
4  3  DAL  10:00    1
>>> vol_sum = sum(df.loc[(df['arv']=='10:00') & (df['abr']=='DAL')]['vol'])
>>> print(f"total vol at 10:00 is: {vol_sum}")
"total vol at 10:00 is: 7"

与dukkee相比没有什么好处:不需要使用集合,列表理解比循环快!请注意,在您的一个词典中,有两个'DAL'作为键,因此第一个被删除

相关问题 更多 >

    热门问题