python:序列化

1. pickle

Python提供了pickle模块来实现序列化。
序列化dic:
pickle.dumps()方法把任意对象序列化成一个bytes

>>> import pickle
>>> d = {'name': 'Luffy', 'age': 18, 'score': 100}
>>> pickle.dumps(d) 
b'\x80\x03}q\x00(X\x04\x00\x00\x00nameq\x01X\x05\x00\x00\x00Luffyq\x02X\x03\x00\
x00\x00ageq\x03K\x12X\x05\x00\x00\x00scoreq\x04Kdu.'
>>>

pickle.dumps()方法把任意对象序列化成一个bytes,然后就可以把这个bytes写入文件。或者用另一个方法pickle.dump()直接把对象序列化后写入文件:

>>> d = {'name': 'Luffy', 'age': 18, 'score': 100}
>>> f = open('d://test.txt', 'wb')
>>> pickle.dump(d, f)
>>> f.close()
>>>

当我们要把对象从磁盘读到内存时,可以先把内容读到一个bytes,然后用pickle.loads()方法反序列化出对象,也可以直接用pickle.load()方法从文件中直接反序列化出对象:

>>> f = open('d://test.txt', 'rb')
>>> pickle.load(f)
{'name': 'Luffy', 'age': 18, 'score': 100}
>>> f.close()
>>>

注意:因为存在python版本不兼容的问题,所以只能用Pickle保存那些不重要的、不能成功地反序列化也没关系的数据

2. JSON序列化

JSON类型和python类型之间的数据对应:
这里写图片描述

2.1 把python对象变成一个JSON:
>>> import json
>>> d = {'name': 'Luffy', 'age': 18, 'score': 100}
>>> json.dumps(d)
'{"name": "Luffy", "age": 18, "score": 100}'

如果dumps()函数加上参数ensure_ascii:

>>> d = dict(name='路飞', age=18)
>>> s = json.dumps(d, ensure_ascii=True)
>>> s
'{"name": "\\u5c0f\\u660e", "age": 18}'
>>> s = json.dumps(d, ensure_ascii=False)
>>> s
'{"name": "路飞", "age": 18}'

可见,加上ensure_ascii=True转成json字符串的中文会变成ascii码,如果为False就可以输出正常。

2.2 把JSON对象变成python对象:
>>> d_str = '{"name": "Luffy", "age": 18, "score": 100}'
>>> json.loads(d_str)
{'name': 'Luffy', 'age': 18, 'score': 100}
>>>

3. 序列化class

序列化Student()类:

>>> class Student(object):
...     def __init__(self, name, age, score):
...             self.name = name
...             self.age = age
...             self.score = score
...
>>> s = Student('Luffy', 18, 100)
>>> print(json.dumps(s))
Traceback (most recent call last):
...
    raise TypeError(f'Object of type {o.__class__.__name__} '
TypeError: Object of type Student is not JSON serializable
>>>

运行时,却抛出不是一个可序列化为JSON的对象的TypeError错误。
原因是默认情况下,dumps()不知道要怎么把Student()转化成JSON对象,这时,我们可以添加dumps的一个可选参数defalut,default可以把任意一个对象变成一个可序列为JSON的对象,举例:
首先我们要先定义一个把Student对象转成dic的函数:

>>> def student2dic(stu):
...     return {
...             'name' : stu.name,
...             'age' : stu.age,
...             'score': stu.score
...     }
...

执行转换:

>>> print(json.dumps(s, default=student2dic))
{"name": "Luffy", "age": 18, "score": 100}
>>>

但是如果新添加一个类,比如Teacher类,就需要重新定义转换函数,所以我们可以改一下,直接使用class的dic属性:

>>> print(json.dumps(s, default=lambda obj: obj.__dict__))
{"name": "Luffy", "age": 18, "score": 100}

把JSON转成Student:
loads()方法首先转换出一个dict对象,我们传入的object_hook函数负责把dict转换为Student实例:

>>> d_str = '{"name": "Luffy", "age": 18, "score": 100}'
>>> json.loads(d_str, object_hook=dic2student)
<__main__.Student object at 0x000000000226DB70>
>>>

猜你喜欢

转载自blog.csdn.net/qq_29144091/article/details/81484117
今日推荐