初识Json&pickle函数序列化附加shelve模块

  通过例子逐步解释序列化

例子1

1 info={
2     'name':'jack',
3     'age':20
4 }
5 f=open('test.text','w')
6 f.write(info)

因为是字典数据类型,不能写入硬盘,运行出错

例子2

1 info={
2     'name':'jack',
3     'age':20
4 }
5 f=open('test.text','w')
6 f.write(str(info))  #把字典转成字符串

把字典转成字符串数据类型,能写入硬盘,数据从内存写入到硬盘上叫做序列化

例子3

1 f=open('test.text','r')
2 data=f.read()
3 print(data)   #>> {'name': 'jack', 'age': 20}

从硬盘读出数据,是字符串数据类型

例子4

1 f=open('test.text','r')
2 data=f.read()
3 print(data['age'])
以字典方式操作,出错,因为文件里存储的是字符串
例子5
1 f=open('test.text','r')
2 data=eval(f.read())  
3 print(data['age'])
用eval()函数将字符串转成字典读出,从硬盘读出数据到内存也叫反序列化
以上序列化和反序列化实现了把内存的数据对象存储到硬盘上,再读回来,相当于虚拟机挂起,又重新读取运行
以上的序列化和反序列化都是简单、不标准的

如要通用、标准的序列化和反序列化,需要用到Json模块里的dumps()和loads()
例子6
1 import json
2 info={
3     'name':'jack',
4     'age':20
5 }
6 f=open('test.text','w')
7 #print(json.dumps(info))  #转成字符串输出
8 f.write(json.dumps(info))  #转成字符串存储到文件

序列化

例子7

1 import json
2 f=open('test.text','r')
3 data=json.loads(f.read()) #反序列化
4 print(data['age'])  #>>20
json只能处理简单的数据类型,像列表、字典、字符串等,因为各语言的对象、类等都不相同
json是所有编程语言都通用的,所有语言都支持json。
json主要的作用是不同语言进行数据交互,已经成为主流的不同平台的数据交换,逐步取代XML
json可以dumps多次,但只能loads一次,规定要求dumps一次,loads一次

例子8
 1 import json
 2 def sayhi(name):
 3     print('hello',name)
 4 
 5 info={
 6     'name':'jack',
 7     'age':20,
 8     'func':sayhi  #sayhi()函数的内存地址
 9 }
10 f=open('test.text','w')
11 f.write(json.dumps(info)) #>>TypeError: Object of type 'function' is not JSON serializable
12                           #“函数”的对象不是JSON序列化类型
13 f.close()

Json不能处理复杂的,带有函数的数据交互

这时需要用到pickle模块,pickle用法与Json完全一样,只不过换个名字而已

例子9

 1 import pickle
 2 #序列化
 3 def sayhi(name):
 4     print('hello',name)
 5 
 6 info={
 7     'name':'jack',
 8     'age':20,
 9     'func':sayhi  #sayhi()函数的内存地址
10 }
11 f=open('test.text','wb')
12 #print(pickle.dumps(info)) #>>b'\x80\x03}q\x00(X\x04\x00.....输出二进制所以要由'w''wb'
13 f.write(pickle.dumps(info))  #可以写入pickle专门的字符存储在文件
14 #简写:pickle.dump(info,f)
15 f.close()

反序列化

1 import pickle
2 f=open('test.text','rb')  #注意'rb'
3 data=pickle.loads(f.read()) #反序列化
4 print(data)      >>AttributeError: Can't get attribute 'sayhi' on <module '__main__' from 'D:/T..
5      

出错,说明sayhi()函数的内存地址随着序列化文件释放了,对象就没找到,如要序列化就把sayhi()拷贝过来

改进如下:例子10

 1 import pickle
 2 def sayhi(name):
 3     print('hello',name)  #反序列化时只要函数名一样,可以更改函数内容
 4 
 5 f=open('test.text','rb')  #注意'rb'
 6 data=pickle.loads(f.read()) #反序列化
 7 #简写:data=pickle.load(f)
 8 print(data) #>>{'name': 'jack', 'age': 20, 'func': <function sayhi at 0x00000000003D3EA0>}
 9 print(data['func']('Alice'))   #>>hello Alice
10 f.close()

反序列化成功

pickle 最终实现了函数的序列化,但pickle只能在本语言内使用,java是不认识pickle数据类型的


shelve模块是一个简单的k,v将内存数据通过文件持久化的模块,可以持久化任何pickle可支持的python数据格式
 1 import shelve
 2 import datetime
 3 
 4 #写入
 5 d = shelve.open('shelve_test')  # 打开一个文件
 6 info={'age:22','job:it'}
 7 name = ["alex", "rain", "test"]
 8 d["name"] = name  # 持久化列表
 9 d["info"] = info  # 持久化类
10 d["date"] = datetime.datetime.now()
11 
12 d.close()
 1 import shelve
 2 import datetime
 3 
 4 #读出
 5 d=shelve.open('shelve_test')
 6 print(d.get('name'))
 7 print(d.get('info'))
 8 print(d.get('date'))
 9 
10 d.close()

 


















 

 






 

posted @ 2018-04-25 14:10  路飞2018  阅读(164)  评论(0编辑  收藏  举报