简单介绍Python中的JSON使用


Posted in Python onApril 28, 2015

JSON进阶

Python的dict对象可以直接序列化为JSON的{},不过,很多时候,我们更喜欢用class表示对象,比如定义Student类,然后序列化:

import json

class Student(object):
  def __init__(self, name, age, score):
    self.name = name
    self.age = age
    self.score = score

s = Student('Bob', 20, 88)
print(json.dumps(s))

运行代码,毫不留情地得到一个TypeError:

Traceback (most recent call last):
 ...
TypeError: <__main__.Student object at 0x10aabef50> is not JSON serializable

错误的原因是Student对象不是一个可序列化为JSON的对象。

如果连class的实例对象都无法序列化为JSON,这肯定不合理!

别急,我们仔细看看dumps()方法的参数列表,可以发现,除了第一个必须的obj参数外,dumps()方法还提供了一大堆的可选参数:

https://docs.python.org/2/library/json.html#json.dumps

这些可选参数就是让我们来定制JSON序列化。前面的代码之所以无法把Student类实例序列化为JSON,是因为默认情况下,dumps()方法不知道如何将Student实例变为一个JSON的{}对象。

可选参数default就是把任意一个对象变成一个可序列为JSON的对象,我们只需要为Student专门写一个转换函数,再把函数传进去即可:

def student2dict(std):
  return {
    'name': std.name,
    'age': std.age,
    'score': std.score
  }

print(json.dumps(s, default=student2dict))

这样,Student实例首先被student2dict()函数转换成dict,然后再被顺利序列化为JSON。

不过,下次如果遇到一个Teacher类的实例,照样无法序列化为JSON。我们可以偷个懒,把任意class的实例变为dict:

print(json.dumps(s, default=lambda obj: obj.__dict__))

因为通常class的实例都有一个__dict__属性,它就是一个dict,用来存储实例变量。也有少数例外,比如定义了__slots__的class。

同样的道理,如果我们要把JSON反序列化为一个Student对象实例,loads()方法首先转换出一个dict对象,然后,我们传入的object_hook函数负责把dict转换为Student实例:

def dict2student(d):
  return Student(d['name'], d['age'], d['score'])

json_str = '{"age": 20, "score": 88, "name": "Bob"}'
print(json.loads(json_str, object_hook=dict2student))

运行结果如下:

<__main__.Student object at 0x10cd3c190>

打印出的是反序列化的Student实例对象。
小结

Python语言特定的序列化模块是pickle,但如果要把序列化搞得更通用、更符合Web标准,就可以使用json模块。

json模块的dumps()和loads()函数是定义得非常好的接口的典范。当我们使用时,只需要传入一个必须的参数。但是,当默认的序列化或反序列机制不满足我们的要求时,我们又可以传入更多的参数来定制序列化或反序列化的规则,既做到了接口简单易用,又做到了充分的扩展性和灵活性。

Python 相关文章推荐
学习python (2)
Oct 31 Python
python网络编程示例(客户端与服务端)
Apr 24 Python
python 2.6.6升级到python 2.7.x版本的方法
Oct 09 Python
Python 序列的方法总结
Oct 18 Python
python字符串str和字节数组相互转化方法
Mar 18 Python
详解Python中最难理解的点-装饰器
Apr 03 Python
Python操作mongodb数据库进行模糊查询操作示例
Jun 09 Python
Python实现图片识别加翻译功能
Dec 26 Python
在django项目中导出数据到excel文件并实现下载的功能
Mar 13 Python
在tensorflow下利用plt画论文中loss,acc等曲线图实例
Jun 15 Python
Python 如何对文件目录操作
Jul 10 Python
通过实例简单了解Python sys.argv[]使用方法
Aug 04 Python
浅析Python中的序列化存储的方法
Apr 28 #Python
详解在Python和IPython中使用Docker
Apr 28 #Python
在Python程序中进行文件读取和写入操作的教程
Apr 28 #Python
介绍Python中的文档测试模块
Apr 28 #Python
Django中几种重定向方法
Apr 28 #Python
详解Python的单元测试
Apr 28 #Python
Python xlrd读取excel日期类型的2种方法
Apr 28 #Python
You might like
自制PHP框架之模型与数据库
2017/05/07 PHP
PHP获取日期对应星期、一周日期、星期开始与结束日期的方法
2018/06/22 PHP
PHP常用函数之获取汉字首字母功能示例
2019/10/21 PHP
php7连接MySQL实现简易查询程序的方法
2020/10/13 PHP
{}与function(){}选用空对象{}来存放keyValue
2012/05/23 Javascript
jquery实现div阴影效果示例代码
2013/09/16 Javascript
javaScript使用EL表达式的几种方式
2014/05/27 Javascript
jQuery实现图片文字淡入淡出效果
2015/12/21 Javascript
NodeJS创建基础应用并应用模板引擎
2016/04/12 NodeJs
谈一谈bootstrap响应式布局
2016/05/23 Javascript
React Native时间转换格式工具类分享
2017/10/24 Javascript
JS散列表碰撞处理、开链法、HashTable散列示例
2019/02/08 Javascript
jQuery each和js forEach用法比较
2019/02/27 jQuery
vue实现lodop打印功能的示例
2020/11/11 Javascript
python append、extend与insert的区别
2016/10/13 Python
Anaconda 离线安装 python 包的操作方法
2018/06/11 Python
Python3 Post登录并且保存cookie登录其他页面的方法
2018/12/28 Python
解决python测试opencv时imread导致的错误问题
2019/01/26 Python
详解WebSocket跨域问题解决
2018/08/06 HTML / CSS
美国专营婴幼儿用品的购物网站:buybuy BABY
2017/01/01 全球购物
美国顶级户外凉鞋品牌:Chacos
2017/03/27 全球购物
巴西在线鞋店:Shoestock
2017/10/28 全球购物
英国最大的户外商店:Go Outdoors
2019/04/17 全球购物
英语专业毕业个人求职自荐信
2013/09/21 职场文书
成人教育自我鉴定
2013/11/01 职场文书
电子商务专业自我鉴定
2013/12/18 职场文书
军训生自我鉴定范文
2013/12/27 职场文书
行政办公室岗位职责
2014/03/18 职场文书
抗震救灾标语
2014/06/26 职场文书
政府班子四风问题整改措施思想汇报
2014/10/08 职场文书
2014年幼儿园个人工作总结
2014/11/10 职场文书
2016年小学生新年寄语
2015/08/18 职场文书
离婚协议书范本(2016最新版)
2016/03/18 职场文书
微信小程序实现录音Record功能
2021/05/09 Javascript
Mysql基础知识点汇总
2021/05/26 MySQL
React列表栏及购物车组件使用详解
2021/06/28 Javascript