Bootstrap

python: 如何将自定义对象和函数方法对象序列化保存,然后再反序列化取出使用

1. Json序列化

  • 在python中对于一般数据的序列化保存经常使用的就是json序列化
  • json序列化可序列的对象: 一般数据类型列表,字典,字符串,数字,布尔值,None等
json可以序列化的对象类型:
	基本数据类型:
		None
		布尔值:True, False
		数字:整数和浮点数
		字符串:str
	
	序列和映射类型:
		列表:list
		元组:tuple(会被转换为 JSON 数组)
		字典:dict
  • 那么自定义对象和函数方法可以通过json序列化吗?
class Person:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def greet(self):
        return f"Hello, my name is {self.name}"


person = Person("abc", 10)

with open("test.json", "w", encoding="utf-8", errors='ignore') as f:
    data = json.dumps(person)
    f.write(data)
# ==>报错 TypeError: Object of type Person is not JSON serializable
  • 所以如果想把类实例和方法序列化,使用json是不行的

2. Pickle序列化

-Pickle是Python标准库中的一个模块,用于将Python对象序列化(pickling)为二进制数据,以及从二进制数据反序列化(unpickling)为Python对象。这个模块对于在不同的Python程序之间传递数据或将数据存储到文件中非常有用。pickle模块支持几乎所有的Python对象,包括自定义对象,但不适用于存储与Python解释器状态相关的对象,如打开的文件、套接字连接等。
详细信息可点击链接参考

  • 在test1.py里面把对象序列化后放到本地文件test.pkl里面
  • 然后在test2,py反序列化test.pkl文件里面的数据,获取对象使用
# test1.py
import pickle

class Person:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def greet(self):
        return f"Hello, my name is {self.name}"


person = Person("abc", 10)

# 序列化
person_pickle = pickle.dumps({"person": person}) # person_pickle数据类型为二进制
with open("test.pkl", "wb") as f:
    f.write(person_pickle)

#with open("test.pkl", "wb") as f:
 #   person_data = {"person": person}
  #  pickle.dump(person_data, f)
  • 以下会报错是因为py文件里面没有保存实例的类
# test2.py
import pickle

# 反序列化
with open("test.pkl", "rb") as f:
    data = pickle.loads(f.read())
print(data)
# 报错AttributeError: Can't get attribute 'Person' on <module '__main__' from 'D:\\text\\test2.py'>
  • 以下为正确的引用方式
# test2.py
import pickle


class Person:
    def __init__(self, name, age):
        self.name = name
        self.age = age

    def greet(self):
        return f"Hello, my name is {self.name}"


# 反序列化
with open("test.pkl", "rb") as f:
    data = pickle.load(f)
print(data)
# ==>{'person': <__main__.Person object at 0x000001CB1FE19E48>}
;