import json from datetime import datetime, date # res = {'1': datetime.today(), '2': date.today()} # 第一次序列化 # print(json.dumps(res)) # TypeError: Object of type 'datetime' is not JSON serializable # 因为datetime.today()和date.today()是对象,不在json序列化的范围内 # 方法一: # 将字典中的值变成可序列化类型,可以手动转成字符串格式 # res1 = 'datetime.today()' # res2 = 'date.today' # res = {'1': res1, '2': res2} # 第二次序列化 # print(json.dumps(res)) # {"1": "datetime.today()", "2": "date.today"} # 因为json可以默认可以转化的数据类型包含字符串,所以在转换之后就可以正常序列化了 # 但是方法过于low bee # 所以 >>> 方法二: ''' 分析步骤: 我们要序列化的内容中有datetime.today()这个对象,而dump不支持对象的序列化 所以就查看dump方法的源码,发现里面有个cls=None的参数,表明你传入的对象默认没有类,并且返回的是cls=JSONEncoder 说明此时cls继承于JSONEncoder,所以我们进一步去JSONEncoder里面查看源码 在JSONEncoder类里面发现一个default方法与第一次序列化时候的报错类型一样,所以我们可以通过修改default方法来达成我们的目的 因为JSONEncoder属于json模块的,所以继承的时候要写json.JSONEncoder ''' class MyJson(json.JSONEncoder): # 定义一个自己的类,并为其指定父类 def default(self, o): # 重新定义父类中的default方法 o代表传入的参数 if isinstance(o, datetime): # 判断如果传入的对象o属于datetime类,则返回o对象的格式化时间,并且python默认输出值是字符串(间接转为字符串) return o.strftime('%Y - %m - %d %X') elif isinstance(o, date): # 判断如果传入的对象o属于date类,则返回o对象的格式化时间,并且python默认输出值是字符串(间接转为字符串) return o.strftime('%Y - %m - %d') else: # 对象o既不属于datetime,也不属于date类,那么就默认使用父类中的方法,所以在这里就再次调用父类的方法,并且需要传入参数 return super().default(self, o) res = {'1': datetime.today(), '2': date.today()} # 第三次序列化 print(json.dumps(res, cls=MyJson)) # {"1": "2019 - 08 - 06 19:12:33", "2": "2019 - 08 - 06"} # 序列化成功
json可序列化的python数据类型有:
| Python | JSON |
+===================+===============+
| dict | object | 字典数据类型
+-------------------+---------------+
| list, tuple | array | 列表,元祖数据类型
+-------------------+---------------+
| str | string | 字符串数据类型
+-------------------+---------------+
| int, float | number | 整型和浮点数据类型
+-------------------+---------------+
| True | true | 布尔值 True
+-------------------+---------------+
| False | false | 布尔值 False
+-------------------+---------------+
| None | null + 空