python基础之 序列 pickle&json

内容梗概:
1. 什么是序列化
2. pickle(重点)
3. shelve
4. json(重点)
5. configparser模块

1. 什么是序列化
在我们存储数据或者网络传输数据的时候. 需要对我们的对象进行处理.把对象处理理成方便便存储和传输的数据格式.
这个过程叫序列化.不同的序列化,结果也不同.但是目的是⼀样的. 都是为了存储和传输.
在python中存在三种序列化方案.
1. pickle.可以将我们python中的任意数据类型转化成bytes并写入到文件中.也可以把文件中写好的bytes转换回python的数据.这个过程被称为反序列列化
2. shelve.简单另类的⼀种序列化的方案.有点儿类似后面我们学到的redis. 可以作为一种小型的数据库来使用
3. json. 将python中常见的字典,列列表转化成字符串串.是目前前后端数据交互使⽤用频率最高的一种数据格式.


2.pickle(重点)
pickle用起来很简单. 说白了. 就是把我们的python对象写入到文件中的一种解决方案.
但是写入到文件的是bytes.所以这东西不是给人看的.是给机器看的.
import pickle
class Cat:
def __init__(self, name, age):
self.name = name
self.age = age
def catchMouse(self):
print(self.name, "抓老鼠")
c = Cat("jerry", 18)
bs = pickle.dumps(c) # 序列化⼀一个对象.
print(bs) # ⼀一堆⼆进制. 看不不懂
# 反序列化,转回python数据
cc = pickle.loads(b'\x80\x03c__main__\nCat\nq\x00)\x81q\x01}q\x02(X\x04\x00\x00\x00nameq\x03X\x05\x00\x00\x00jerryq\x04X\x03\x00\x00\x00ageq\x05K\x12ub.') # 把⼆进制反序列列化成我们的对象
print(cc.name) # 猫依然是猫.

tips:pickle中的dumps可以序列列化一个对象.loads可以反序列化一个对象.我们使用dump还可以直接把一个对象写入到文件中

lst = [Cat("jerry", 19), Cat("tommy", 20), Cat("alpha", 21)]
f = open("cat", mode="wb")
for el in lst:
pickle.dump(el, f) # 写入到文件中
f.close()
f = open("cat", mode="rb")
for i in range(len(lst)):
cc = pickle.load(f) # 从文件中读取对象
cc.catchMouse()

这样写并不够好. 因为读的时候. 并不能知道有多少对象要读. 这里记住, 不能一行行读.
那真的要写入或者读取多个内容怎么办? 很简单. 装list里. 然后读取和写入都用

lst = [Cat("jerry", 19), Cat("tommy", 20), Cat("alpha", 21)]
f = open("cat", mode="wb")
pickle.dump(lst, f)
f = open("cat", mode="rb")
ll = pickle.load(f)
for el in ll:
el.catchMouse()
记住一点, pickle序列化的内容是⼆进制的内容(bytes)不是给人看的.

3.shelve
shelve提供python的持久化操作.什么叫持久化操作呢?就是把数据写到硬盘上.在操作shelve的时候非常的像操作⼀个字典.
实例:
import shelve
s1 = shelve.open("sylar")
s1["jay"] = {"name":"周杰伦", "age":18, "hobby":"哄小孩"}
print(s1["jay"])
s1.close

如何修改呢?此处有深坑,请注意!!!
import shelve
s1 = shelve.open("sylar")
s1["jay"]["age"] = 15
print(s1["jay"]["age"]) # 结果为18,没有修改成功
s1.close()

可采用此种办法. writeback = True
import shelve
s1 = shelve.open("sylar",writeback = True) #开启回写功能
s1["jay"]["age"] = 15
print(s1["jay"]["age"]) # 结果为15,修改成功
s1.close()

writeback=True可以动态的把我们修改的信息写入到文件中. ⽽而且这个东西还可以删除数据. 就像字典一样.
s = shelve.open("sylar", writeback=True)
del s['jay']
s.close()
s = shelve.open("sylar")
print(s['jay']) # 报错了了, 没有了
s.close()
s = shelve.open("sylar", writeback=True)
s['jay'] = "周杰伦"
s['wlj'] = "王⼒宏"
s.close()
s = shelve.open("sylar")
for k in s: # 像字典⼀一样遍历
print(k)
print(s.keys()) # 拿到所有key的集合
for k in s.keys():
print(k)
for k, v in s.items(): # 像字典⼀一样操作
print(k, v)
s.close()


4. json(重点)
json是我们前后端交互的枢纽.相当于编程界的普通话.大家沟通都用json.因为json的语法格式可以完美的表示出一个对象

例1:字典转化成我们的json格式的字符串
import json
dic = {"a": "女王", "b": "萝莉", "c": "小清新","d":False}
s1 = json.dumps(dic,ensure_ascii=False)
print(s1)

例2:json格式的字符串转化成我们的字典
s = '{"a": "女王", "b": "萝莉", "c": "小清新", "d": false}'
s1 = json.loads(s)
print(s1)

例3:json也可以像pickle一样把序列化的结果写入到文件中和从文件中读取结果.
import json
dic = {"a": "女王", "b": "萝莉", "c": "小清新","d":False}
with open("test_json",mode="w",encoding="utf-8")as f1:
json.dump(dic,f1,ensure_ascii=False)

同样的也可以读
with open("test_json",mode="r",encoding="utf-8")as f1:
dic1 = json.load(f1)
print(dic1)

例4:如何把对象写进文件??
import json
class Person:
def __init__(self, firstName, lastName):
self.firstName = firstName
self.lastName = lastName

#把json换成对象
s = '{"firstName": "尼古拉斯", "lastName": "刘能"}'
def func(dic):
return Person(dic['firstName'], dic["lastName"])
#
p = json.loads(s, object_hook=func) # 通过函数func把字典转换回对象
print(p.firstName, p.lastName)

把对象转换成json
p = Person("尼古拉斯", "刘能")
s = json.dumps(p.__dict__, ensure_ascii=False) # 方案一, 转的是字典

方案二:
def func(obj):
return {
"firstName": obj.firstName,
"lastName": obj.lastName
}
s = json.dumps(p, default=func, ensure_ascii=False) # 方案二 转化的也是字典
print(s)



向文件中写入多个json字符串怎么写??读怎么读??

dic1 = {"name":'毒液', "评分": "0.9"}
dic2 = {"name":'与神同行', "评分": "10"}
dic3 = {"name":'看不见的客人', "评分": "9.5"}

lst = [dic1, dic2, dic3]
f = open("movie.json", mode="w", encoding="utf-8")
for d in lst:
s = json.dumps(d, ensure_ascii=False)
f.write(s+"\n")

f = open("movie.json", mode="r", encoding="utf-8")
dic1 = json.load(f) # 当json文件中保存多个json的时候不能一次性全部都读取出来
print(dic1)

f = open("movie.json", mode="r", encoding="utf-8")
for line in f:
line = line.strip()
if line == "":
continue
else:
d = json.loads(line) # 一行一行的处理
print(d)

tips:可以写,但必须一行一行写,不然没办法读,读的时候也必须一行一行的读

5.configparser模块
该模块适用于配置文件的格式与windows ini文件类似,可以包含一个或多个节(section)每个节可以有多个参数(键=值).
import configparser

config = configparser.ConfigParser() # 创建对象

config['DEFAULT'] = { # 特殊
"name":"腾讯qq木马",
"time":"qq更新时间",
"version":"1.0"
}
config['SERVER_1'] = {
"IP":"192.168.1.123",
"port":"12306"
}
config['SERVER_2'] = {
"IP":"192.168.1.178",
"port":"12311"
}
config['SERVER_3'] = {
"IP":"192.168.1.176",
"port":"12312"
}

# 写入到文件
config.write(open("qq.ini", mode="w", encoding="utf-8"))

# 读取内容
config = configparser.ConfigParser()
config.read("qq.ini", encoding="utf-8") # 此时我们把文件中的内容读取到config
print(config['SERVER_1']['IP']) # 字典
print(config['SERVER_2']['name'])
print(config.get("SERVER_3", "IP")) # 字典

for k, v in config['DEFAULT'].items():
print(k, v)

posted @ 2018-11-15 21:27  Mixtea  阅读(162)  评论(0编辑  收藏  举报