【问题标题】:Fill Column using a for loop from multiple dictionaries使用来自多个字典的 for 循环填充列
【发布时间】:2020-08-29 04:12:28
【问题描述】:

我有多个字典,我正在尝试将它们附加到一个数据帧中。

import pandas as pd
dict1 = {'A': '1', 'B': [{'att1': 'value1', 'att2': 'value2'}]}
dict2 = {'A': '2', 'B': [{'att1': 'value3', 'att2': 'value4'}]}
df = pd.DataFrame()
dict = [dict1, dict2]
df['A'] = []
for i in range(0, 2):
    df = df.append(dict[i]['B'])
    df['A'] = (dict[i]['A'])

这给了

   A    att1    att2
0  2  value1  value2
0  2  value3  value4

无论如何我都想要

   A    att1    att2
0  1  value1  value2
0  2  value3  value4

有人可以帮忙吗?

【问题讨论】:

    标签: python pandas dictionary for-loop append


    【解决方案1】:

    从艾伦那里搬来,我最终得到了我需要的东西:

    dict1 = {'A': '1', 'B': [{'att1': 'value1', 'att2': 'value2'}]}
    dict2 = {'A': '2', 'B': [{'att1': 'value3', 'att2': 'value4'}]}
    dict = [dict1, dict2]
    
    df = pd.DataFrame()
    df['A'] = []
    for i in range(0, 2):
        df = df.append(pd.concat([pd.DataFrame(dict[i])]).pipe(lambda x: pd.concat([x, x.B.apply(pd.Series)], 1)).drop('B', 1))
    print(df)
    

    给予

       A    att1    att2
    0  1  value1  value2
    0  2  value3  value4
    

    【讨论】:

      【解决方案2】:

      你可以使用json normalize:

      from pandas import json_normalize
      def normalize(mapping):
          return json_normalize(mapping, 'B', 'A')
      
      pd.concat((normalize(dict1),normalize(dict2)))
          att1    att2    A
      0   value1  value2  1
      0   value3  value4  2
      

      【讨论】:

      • 这似乎只适用于两个字典.. 我的最终目标是编写一个 for 循环来组合尽可能多的字典...
      【解决方案3】:

      一个基于pd.json_normalize 的优雅解决方案是可能的,但是一个 这种方式的障碍是您的两个字典中的 B 键都包含 具有单个元素的 list,而它们应该只包含 这个元素。

      为了克服这个障碍,运行一个列表推导,创建一个列表 字典,使用嵌套字典理解转换这样的列表 进入底层元素:

      dct = [ { k: v[0] if isinstance(v, list) else v for k, v in d.items()}
          for d in [dict1, dict2]]
      

      结果是:

      [{'A': '1', 'B': {'att1': 'value1', 'att2': 'value2'}},
       {'A': '2', 'B': {'att1': 'value3', 'att2': 'value4'}}]
      

      那你可以拨打df = pd.json_normalize(dct),得到:

         A  B.att1  B.att2
      0  1  value1  value2
      1  2  value3  value4
      

      剩下要做的唯一一件事就是重命名两个 B.... 列:

      df.rename(columns={'B.att1' : 'att1', 'B.att2' : 'att2'}, inplace=True)
      

      现在你得到了你想要的,即:

         A    att1    att2
      0  1  value1  value2
      1  2  value3  value4
      

      注意:pd.json_normalize 出现在 Pandas 版本 1.0 中。 早些时候,此方法被“隐藏”在 pandas.io.json 包中。

      【讨论】:

        【解决方案4】:

        你可以使用 pd.concat

        (
            pd.concat([pd.DataFrame(dict1), pd.DataFrame(dict2)])
            .pipe(lambda x: pd.concat([x,x.B.apply(pd.Series)],1))
            .drop('B',1)
        )
        
            A   att1    att2
        0   1   value1  value2
        0   2   value3  value4
        

        【讨论】:

        • 如果我对此使用 for 循环,它只会给出 dict[1]。我的最终目标是编写一个 for 循环来组合尽可能多的字典。
        • 我在 for 循环中使用了 append 函数,它给出了我想要的。
        【解决方案5】:

        构建要附加的行:

        for i in range(0, 2):
            row = dict[i]['B']
            row[0].update({'A': dict[i]['A']})
            df = df.append(row)
            print(df)
        

        输出:

           A    att1    att2
        0  1  value1  value2
        
           A    att1    att2
        0  1  value1  value2
        0  2  value3  value4
        

        如果您研究如何从 dict(或 JSON 对象)构建整个数据框,这对您来说可能会更顺畅。我只解决了眼前的问题。

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2021-07-06
          • 1970-01-01
          • 1970-01-01
          • 2015-07-28
          • 2020-05-30
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多