如何按键对不均匀的字典进行排序并创建CSV

时间:2014-11-06 12:27:01

标签: python sorting python-2.7 csv

我有一个python字典,每个KEY可以有一个可变数量的VALUES(排列在列表中)。

例如:

{'607': [36146], '448': [50890, 44513], '626': [44349, 44436]}

我想要做的是使用如下格式生成此信息的CSV:

 448 , 607 , 626
50890,36146,44349
44513,     ,44436

目前我的代码可以生成这样的CSV,唯一的问题是CSV的列没有按照KEY的升序数字顺序排序。到目前为止我的代码如下:

csv_file = 'file.csv'
with open(csv_file, 'wb') as fd:
    writer = csv.writer(fd, delimiter = ',')

    # Format headers for aesthetics
    csv_headers = [' {} '.format(elem) for elem in dictionary.keys()]

    writer.writerow(headers)

    # Format data to create convenient csv format
    csv_data = itertools.izip_longest(*dictionary.values(), fillvalue = '     ')
    writer.writerows(csv_data)

正如你所看到的那样,我从VALUE中拆分KEY并分别编写它们,但如果我想用KEY对列进行排序,我想这可能不是解决这个问题的最佳方法。因此,我希望有人可以指出我在正确(和最pythonic)的方向。

2 个答案:

答案 0 :(得分:2)

您有两种选择:

  • 对键进行排序,然后以相同的顺序提取值,而不是依赖dictionary.values()
  • 使用csv.DictWriter() object并按行生成字典。

选项1如下所示:

csv_file = 'file.csv'
with open(csv_file, 'wb') as fd:
    writer = csv.writer(fd, delimiter=',')

    keys = sorted(dictionary) 
    # Format headers for aesthetics
    headers = [' {} '.format(key) for key in keys]
    writer.writerow(headers)

    # Format data to create convenient csv format
    csv_data = itertools.izip_longest(*(dictionary[key] for key in keys),
                                      fillvalue='     ')
    writer.writerows(csv_data)

使用DictWriter看起来像:

csv_file = 'file.csv'
with open(csv_file, 'wb') as fd:
    writer = csv.DictWriter(
        fd, sorted(dictionary), delimiter=',')
    # write formatted headers
    writer.writerow({k: ' {} '.format(k) for k in dicitonary})

    csv_data = itertools.izip_longest(*dictionary.values(), fillvalue='     ')
    writer.writerows(dict(zip(dictionary, row)) for row in csv_data)

答案 1 :(得分:1)

我去排序并最终得到keyiterable列表的转置元组,然后从那里开始:

import csv
from itertools import izip_longest

d = {'607': [36146], '448': [50890, 44513], '626': [44349, 44436]}

with open('output.csv', 'wb') as fout:
    csvout = csv.writer(fout)
    header, rows = zip(*sorted((k, iter(v)) for k, v in d.iteritems()))
    csvout.writerow(format(el, '^5') for el in header)
    csvout.writerows(izip_longest(*rows, fillvalue='     '))