如何从python中的json文本解析类对象列表?

时间:2014-08-28 17:27:50

标签: python json python-2.7

我使用 json 库来解码json文本

import json

我有一个像这样定义的Party类:

class Party(object):
    id = ""
    code = ""
    create_date = ""
    citizenship = ""

object_hook方法:

def as_party(d):
    p = Party()
    p.__dict__.update(d)
    return p

我可以使用此方法从json文本中获取Party对象:

def parse_as(s, typo_class):
    return json.loads(str(s), object_hook=typo_class)

当我在包含编码Party类的json文本上调用 parse_as 方法时,我得到一个Party类型的对象。

json_text = {'id': 2, 'code': '2', 'create_date': null, 'citizenship': null}
party1 = parse_as(json_text, as_party)

我可以这样称呼它的属性:

print party1.code

我的问题是让 parse_as 方法能够解析包含列表的Party对象的json文本,如下所示:

json_text = [{'id': 2, 'code': '2', 'create_date': null, 'citizenship': null}, {'id': 5, 'code': '3', 'create_date': null, 'citizenship': null}, {'id': 6, 'code': '8', 'create_date': null, 'citizenship': null}]

请帮助我,并提前致谢!

2 个答案:

答案 0 :(得分:2)

对象钩子需要更改

def as_party(d):
    if isinstance(d, dict):
      p = Party()
      p.__dict__.update(d)
    elif isinstance(d, list):
     out = []
     for i in d:
       n = Party()
       n.__dict__.update(i)
       out.append(n)
     p = out
    else:
      raise Exception('got non-dict value %s' % d)
    return p
不过,我不会使用__dict__,宁愿使用带有一些前缀的setattr ...

因为如果键值是python关键字,那就不好了。

>>> a = Foo()
>>> a.__dict__['except'] = 1
>>> a.except
  File "<stdin>", line 1
    a.except
           ^
SyntaxError: invalid syntax

答案 1 :(得分:1)

对于使用setattr的不同方法并避免使用python关键字进行整理:

def as_party(d):
    if isinstance(d, dict):
      p = Party()
      for k,v in d.iteritems():
        setattr(p, 'v_%s' % k, v) # you can assign any prefix you want
    elif isinstance(d, list):
     out = []
     for i in d:
       n = Party()
       for k,v in i.iteritems():
         setattr(n, 'v_%s' % k, v)
       out.append(n)
     p = out
    else:
      raise Exception('got non-dict value %s' % d)
    return p

但是你必须使用我们合并的前缀来访问那些值:

print party.v_for,party.v_except#etc ..

通常,您可以计算出不允许使用python关键字的代码:

import keyword

def as_party(d):
    if isinstance(d, dict):
      p = Party()
      for k,v in d.iteritems():
        if keyword.iskeyword(k):
          raise Exception('Cannot accept %s as a property name. That is resrved python keyword' % k)
        setattr(p, k, v) # you can assign any prefix you want
    elif isinstance(d, list):
     out = []
     for i in d:
       n = Party()
       for k,v in i.iteritems():
        if keyword.iskeyword(k):
          raise Exception('Cannot accept %s as a property name. That is resrved python keyword' % k)
         setattr(n, k, v)
       out.append(n)
     p = out
    else:
      raise Exception('got non-dict value %s' % d)
    return p