从flat csv创建嵌套的JSON

时间:2011-10-30 23:39:28

标签: python json csv nested flat

尝试根据此示例从csv创建4个深层嵌套JSON:

Region,Company,Department,Expense,Cost
Gondwanaland,Bobs Bits,Operations,nuts,332
Gondwanaland,Bobs Bits,Operations,bolts,254
Gondwanaland,Maureens Melons,Operations,nuts,123

在每个级别,我想总结成本并将其包含在相关级别的输出JSON中。

输出的JSON的结构应如下所示:

    {
          "id": "aUniqueIdentifier", 
          "name": "usually a nodes name", 
          "data": [
                {
                      "key": "some key", 
                      "value": "some value"
                }, 
                {
                      "key": "some other key", 
                      "value": "some other value"
                }
          ], 
          "children": [/* other nodes or empty */ ]
    }

(参考:http://blog.thejit.org/2008/04/27/feeding-json-tree-structures-to-the-jit/

根据python中的递归函数思考,但到目前为止这种方法还没有取得多大成功......对于快速简便的解决方案的任何建议都非常感激?

更新: 渐渐放弃了总结成本的想法,因为我无法弄明白:(。我还不是一个python编码器)!只需能够生成格式化的JSON就足够了,如果必须的话,我可以稍后插入数字。

一直在阅读,谷歌搜索和阅读解决方案,并在途中学到了很多,但仍然没有成功从上面的CSV结构创建我的嵌套JSON文件。网上某处必须是一个简单的解决方案吗?也许其他人的搜索条件更幸运了????

1 个答案:

答案 0 :(得分:8)

以下是一些提示。

使用 csv.reader 将输入解析为列表列表:

>>> rows = list(csv.reader(source.splitlines()))

循环列表以构建字典并总结成本。根据您希望创建的结构,构建可能如下所示:

>>> summary = []
>>> for region, company, department, expense, cost in rows[1:]:
    summary.setdefault(*region, company, department), []).append((expense, cost))

使用 json.dump

写出结果
>>> json.dump(summary, open('dest.json', 'wb'))

希望下面的递归函数能帮助您入门。它根据输入构建树。请注意您希望叶子的类型,我们将其标记为“成本”。你需要详细说明建立你想要的确切结构的函数:

import csv, itertools, json

def cluster(rows):
    result = []
    for key, group in itertools.groupby(rows, key=lambda r: r[0]):
        group_rows = [row[1:] for row in group]
        if len(group_rows[0]) == 2:
            result.append({key: dict(group_rows)})
        else:
            result.append({key: cluster(group_rows)})
    return result

if __name__ == '__main__':
    s = '''\
Gondwanaland,Bobs Bits,Operations,nuts,332
Gondwanaland,Bobs Bits,Operations,bolts,254
Gondwanaland,Maureens Melons,Operations,nuts,123
'''
    rows = list(csv.reader(s.splitlines()))
    r = cluster(rows)
    print json.dumps(r, indent=4)