如何将JSON数据转换为Python对象?
我想把JSON数据转换成Python对象。
我从Facebook的API那里收到了JSON数据对象,我想把它们存储到我的数据库里。
我现在在Django(Python)中的视图是这样的(request.POST
里包含了JSON):
response = request.POST
user = FbApiUser(user_id = response['id'])
user.name = response['name']
user.username = response['username']
user.save()
- 这样做没问题,但我该如何处理复杂的JSON数据对象呢?
- 如果我能把这个JSON对象转换成Python对象,那使用起来不是更方便吗?
32 个回答
146
请查看一下 专门处理 JSON 对象解码 这一部分,内容在 json
的 模块文档中。你可以用它把 JSON 对象解码成特定的 Python 类型。
这里有个例子:
class User(object):
def __init__(self, name, username):
self.name = name
self.username = username
import json
def object_decoder(obj):
if '__type__' in obj and obj['__type__'] == 'User':
return User(obj['name'], obj['username'])
return obj
json.loads('{"__type__": "User", "name": "John Smith", "username": "jsmith"}',
object_hook=object_decoder)
print type(User) # -> <type 'type'>
更新
如果你想通过 json 模块访问字典中的数据,可以这样做:
user = json.loads('{"__type__": "User", "name": "John Smith", "username": "jsmith"}')
print user['name']
print user['username']
就像访问普通字典一样。
187
你可以试试这个:
class User():
def __init__(self, name, username):
self.name = name
self.username = username
import json
j = json.loads(your_json)
u = User(**j)
只需要创建一个新的对象,然后把参数作为一个映射传进去。
你也可以用包含对象的JSON:
import json
class Address():
def __init__(self, street, number):
self.street = street
self.number = number
def __str__(self):
return "{0} {1}".format(self.street, self.number)
class User():
def __init__(self, name, address):
self.name = name
self.address = Address(**address)
def __str__(self):
return "{0} ,{1}".format(self.name, self.address)
if __name__ == '__main__':
js = '''{"name":"Cristian", "address":{"street":"Sesame","number":122}}'''
j = json.loads(js)
print(j)
u = User(**j)
print(u)
693
更新
在Python3中,你可以用一行代码来实现,使用的是 SimpleNamespace
和 object_hook
:
import json
from types import SimpleNamespace
data = '{"name": "John Smith", "hometown": {"name": "New York", "id": 123}}'
# Parse JSON into an object with attributes corresponding to dict keys.
x = json.loads(data, object_hook=lambda d: SimpleNamespace(**d))
print(x.name, x.hometown.name, x.hometown.id)
旧答案(Python2)
在Python2中,你也可以用一行代码来实现,使用的是 namedtuple
和 object_hook
(不过如果有很多嵌套对象的话,这种方法会很慢):
import json
from collections import namedtuple
data = '{"name": "John Smith", "hometown": {"name": "New York", "id": 123}}'
# Parse JSON into an object with attributes corresponding to dict keys.
x = json.loads(data, object_hook=lambda d: namedtuple('X', d.keys())(*d.values()))
print x.name, x.hometown.name, x.hometown.id
或者,为了方便重复使用:
def _json_object_hook(d): return namedtuple('X', d.keys())(*d.values())
def json2obj(data): return json.loads(data, object_hook=_json_object_hook)
x = json2obj(data)
如果你想处理一些不太适合作为属性名的键,可以看看 namedtuple
的 rename
参数。