将字符串转换为有序字典?

Chr*_*ong 5 python dictionary python-2.7

我有一个字符串,基本上包含一堆JSON格式的文本,我最终希望以"漂亮的打印"格式导出到Excel,并使用适当的嵌套缩进等.

为了便于阅读,必须保留密钥/值的原始顺序.我的思维过程是为了实现我想要的

a)使用类似eval之类的东西将字符串转换为字典,以及b)使用集合库中的OrderedDict来保持订单的完整性.

但是我没有得到预期的结果:

In [21]: json_string = str({"id":"0","last_modified":"undefined"})
In [22]: OrderedDict(eval(json_string))
Out[23]: OrderedDict([('last_modified', 'undefined'), ('id', '0')])
Run Code Online (Sandbox Code Playgroud)

我还没有完全弄清楚我将如何以漂亮的打印格式将输出写入excel,但我希望这是相对容易的部分!

jte*_*ace 19

您可以使用JSONDecoderobject_pairs_hook参数将已解码的字典更改为OrderedDict:

import collections
import json

decoder = json.JSONDecoder(object_pairs_hook=collections.OrderedDict)

json_string = '{"id":"0","last_modified":"undefined"}'
print decoder.decode(json_string)
json_string = '{"last_modified":"undefined","id":"0"}'
print decoder.decode(json_string)
Run Code Online (Sandbox Code Playgroud)

这打印:

OrderedDict([(u'id', u'0'), (u'last_modified', u'undefined')])
OrderedDict([(u'last_modified', u'undefined'), (u'id', u'0')])
Run Code Online (Sandbox Code Playgroud)


mgi*_*son 6

首先,你应该考虑使用json(或甚至ast.literal_eval)代替eval.

其次,这不起作用,因为你把它变成普通字典的那一刻,所有的订单都会丢失.如果要将信息放入OrderedDict,则需要自己解析"json".

幸运的是,如果您使用该ast模块,这并不像您想象的那么难.这里我假设字典只包含字符串,但是为了其他目的而不应该太难修改.

s = '{"id":"0","last_modified":"undefined"}'
import ast
from collections import OrderedDict
class DictParser(ast.NodeVisitor):
    def visit_Dict(self,node):
        keys,values = node.keys,node.values
        keys = [n.s for n in node.keys]
        values = [n.s for n in node.values]
        self.od = OrderedDict(zip(keys,values))

dp = DictParser()
dp.visit(ast.parse(s))
ordered_dict = dp.od
print ordered_dict
Run Code Online (Sandbox Code Playgroud)