【问题标题】:How do i convert a dictionary with unequal list as value to csv如何将具有不等列表的字典作为值转换为 csv
【发布时间】:2018-05-02 22:41:02
【问题描述】:

我有一本字典,其中的值不相等

dict_data = {
    "Data 1": ["cool", "fantastic"],
    "Data 2": ["spam", "hello", "howdy", "foo"],
    "Data 3": ["good morning"],
}

我想要这样的输出

Data 1     Data 2  Data 3
cool       spam    good morning
fantastic  hello
           howdy
           foo

我已经尝试过我在这个论坛上找到的这个

def transpose(cols):
    return map(lambda *row: list(row), *cols)

with open('result.csv','w') as out_file:
    writer = csv.writer(out_file,dialect = 'excel')
    headers = dict_data.keys()
    items = transpose(dict_data.values())
    writer.writerow(headers)
    writer.writerows(items)

但它只输出第一行

Data 1     Data 2  Data 3
cool       spam    good morning

【问题讨论】:

    标签: python python-3.x csv


    【解决方案1】:

    您可以通过键中Data之后的尾随值对数据进行排序,然后使用itertools.zip_longest

    import re, csv, itertools
    dict_data = {'Data 2': ['spam', 'hello', 'howdy', 'foo'], 'Data 3': ['good morning'], 'Data 1': ['cool', 'fantastic']}
    sorted_result = sorted(dict_data.items(), key=lambda x:int(re.findall('\d+$', x[0])[0]))
    with open('filename1.csv', 'w') as f:
       write = csv.writer(f)
       write.writerows([[a for a, _ in sorted_result]]+list(itertools.zip_longest(*[b for _, b in sorted_result], fillvalue='')))
    

    输出:

    Data 1,Data 2,Data 3
    cool,spam,good morning
    fantastic,hello,
    ,howdy,
    ,foo,
    

    【讨论】:

      【解决方案2】:

      这可能不是最佳答案,但我总是将要导出为 csv 的数据转换为 pandas 数据框。此解决方案也适用于不相等的列表值。

      data1 = pd.DataFrame(dict_data["Data 1"])
      data2 = pd.DataFrame(dict_data["Data 2"])
      
      master = pd.concat([data1, data2], axis=1) 
      master.to_csv("file_name", encoding='utf-8', index=False, header=None)
      

      【讨论】:

      • 对我来说效果很好。
      • 为正确的工作提供正确的工具。是时候学习熊猫了 :)
      • 是的,我想是的 :-)
      【解决方案3】:

      您的转置想法是处理小数据的好方法。对您来说,出现问题的地方似乎是数据行的长度不均匀。如果在转置之前用空字符串填充短行,一切正常:

      import csv
      
      dict_data = {
          "Data 1": ["cool", "fantastic"],
          "Data 2": ["spam", "hello", "howdy", "foo"],
          "Data 3": ["good morning"],
      }
      
      
      def transpose(cols):
          return map(lambda *row: list(row), *cols)
      
      
      def padright(list_to_be_padded, normalised_length):
          return list_to_be_padded + [''] * (normalised_length - len(list_to_be_padded))
      
      
      no_of_rows_in_csv = max(len(phrases) for phrases in dict_data.values())
      # fieldname is first column (pre-transpose)
      # all lists of phrases normalised to same length
      output_data = [[fieldname] + padright(phrases, no_of_rows_in_csv)
                     for fieldname, phrases in dict_data.items()]
      output_data = transpose(output_data)
      
      
      with open('result.csv','w') as out_file:
          writer = csv.writer(out_file,dialect = 'excel')
          writer.writerows(output_data)
      

      结果:

      Data 2,Data 3,Data 1
      spam,good morning,cool
      hello,,fantastic
      howdy,,
      foo,,
      

      注意:您最好将字段名称/列标题(原始 dict 键)作为转置的一部分处理,而不是单独处理它们。

      最后一件事:迭代 Python 字典不会以定义的顺序返回成员,这就是为什么 Data 2 列首先出现在我的结果中。如果您希望最终数据列按特定顺序排列,请查看 Python 类 OrderedDict,或者,正如另一个答案所述,您可以在转置之前按键对数据进行排序。

      【讨论】:

        猜你喜欢
        • 2017-04-11
        • 1970-01-01
        • 1970-01-01
        • 2021-12-29
        • 1970-01-01
        • 2014-06-23
        • 1970-01-01
        • 2014-04-24
        • 2014-04-06
        相关资源
        最近更新 更多