python建立数据库并序列化_Python之数据序列化(json、pickle、shelve)
一、python類型數據和JSON數據格式互相轉換
pthon 中str類型到JSON中轉為unicode類型,None轉為null,dict對應object
二. 序列化/反序列化
將對象轉換為可通過網絡傳輸或可以存儲到本地磁盤的數據格式(如:XML、JSON或特定格式的字節串)的過程稱為序列化;反之,則稱為反序列化。
三.相關模塊
本節要介紹的就是Python內置的幾個用于進行數據序列化的模塊:
模塊名稱描述提供的api
json
用于實現Python數據類型與通用(json)字符串之間的轉換
dumps()、dump()、loads()、load()
pickle
用于實現Python數據類型與Python特定二進制格式之間的轉換
dumps()、dump()、loads()、load()
shelve
專門用于將Python數據類型的數據持久化到磁盤,shelve是一個類似dict的對象,操作十分便捷
open()
四、json操作
1、json串轉成字典:
(1).loads()方法
1 import json#引用json模塊
2 res=json.loads(s)3 print(res)#打印字典
4 print(type(res))#打印res類型
5 print(res.keys())#打印字典的所有Key
View Code
要先讀文件,然后再轉換:
1 f=open('stus.json',encoding='utf-8')2 content=f.read()#使用loads()方法,需要先讀文件
3 user_dic=json.loads(content)4 print(user_dic)
View Code
(2).load()方法
1 importjson2 f=open('stus.json',encoding='utf-8')3 user_dic=json.load(f)4 print(user_dic)
View Code
(3)區別
loads()傳的是字符串,而load()傳的是文件對象
使用loads()時需要先讀文件再使用,而load()則不用
2、字典轉成json串:
文件里只能寫字符串,但可以把字典轉成json串,json串是字符串,可以存到文件里
(1).dumps()方法
1 stus={'xiaojun':'123456','xiaohei':'7891','abc':'11111'}2 #先把字典轉成json
3 res2=json.dumps(stus)4 print(res2)#打印字符串
5 print(type(res2))#打印res2類型
View Code
.dumps()方法:把字典轉成json串
使用.dumps()方法前,要先打開文件,再寫入:
1 stus={'xiaojun':'123456','xiaohei':'7890','lrx':'111111'}2 res2=json.dumps(stus,indent=8,ensure_ascii=False)3 print(res2)4 with open('stus.json','w',encoding='utf-8') as f:#使用.dumps()方法時,要寫入
5 f.write(res2)
View Code
(2)dump()方法
1 stus={'xiaojun':'123456','xiaohei':'7890','lrx':'111111'}2 f=open('stus2.json','w',encoding='utf-8')3 json.dump(stus,f,indent=4,ensure_ascii=False)
View Code
(3)區別
.dump()不需要使用.write()方法,只需要寫哪個字典、哪個文件即可;而.dumps()需要使用.write()方法寫入
如果要把字典寫到文件里面的時候,dump()好用;但如果不需要操作文件,或需要把內容存到數據庫和Excel,則需要使用dumps()先把字典轉成字符串,再寫入
(4)dump\dumps參數
.dumps\dump中使用參數indent,為字符串換行+縮進:
1 復制代碼2 res2=json.dumps(stus.indent=4)3 print(res2)#打印字符串
4 #結果為:
5 '''
6 {7 "xiaojun": "123456",8 "xiaohei": "7891",9 "lrx": "hailong",10 "tanailing": "111111"11 }12 '''
13 復制代碼
View Code
.dumps\dump中使用參數ensure_ascii,為內容輸出為中文:
1 res2=json.dumps(stus,indent=4,ensure_ascii=False)#為False時內容輸出顯示正常的中文,而不是轉碼
2 print(res2)
View Code
3、不管是dump還是load,帶s的都是和字符串相關的,不帶s的都是和文件相關的。
五、pickle模塊
pickle模塊實現了用于對Python對象結構進行 序列化 和 反序列化 的二進制協議,與json模塊不同的是pickle模塊序列化和反序列化的過程分別叫做 pickling 和 unpickling:
pickling:?是將Python對象轉換為字節流的過程;
unpickling:?是將字節流二進制文件或字節對象轉換回Python對象的過程;
1. pickle模塊與json模塊對比
JSON是一種文本序列化格式(它輸出的是unicode文件,大多數時候會被編碼為utf-8),而pickle是一個二進制序列化格式;
JOSN是我們可以讀懂的數據格式,而pickle是二進制格式,我們無法讀懂;
JSON是與特定的編程語言或系統無關的,且它在Python生態系統之外被廣泛使用,而pickle使用的數據格式是特定于Python的;
默認情況下,JSON只能表示Python內建數據類型,對于自定義數據類型需要一些額外的工作來完成;pickle可以直接表示大量的Python數據類型,包括自定數據類型(其中,許多是通過巧妙地使用Python內省功能自動實現的;復雜的情況可以通過實現specific object API來解決)
2. pickle模塊提供的相關函數
1 pickle模塊提供的幾個序列化/反序列化的函數與json模塊基本一致:2
3 #將指定的Python對象通過pickle序列化作為bytes對象返回,而不是將其寫入文件
4 dumps(obj, protocol=None, *, fix_imports=True)5
6 #將通過pickle序列化后得到的字節對象進行反序列化,轉換為Python對象并返回
7 loads(bytes_object, *, fix_imports=True, encoding="ASCII", errors="strict")8
9 #將指定的Python對象通過pickle序列化后寫入打開的文件對象中,等價于`Pickler(file, protocol).dump(obj)`
10 dump(obj, file, protocol=None, *, fix_imports=True)11
12 #從打開的文件對象中讀取pickled對象表現形式并返回通過pickle反序列化后得到的Python對象
13 load(file, *, fix_imports=True, encoding="ASCII", errors="strict")
View Code
說明:?上面這幾個方法參數中,*號后面的參數都是Python 3.x新增的,目的是為了兼容Python 2.x,具體用法請參看官方文檔。
3.實例:內置數據類型的序列化/反序列化
1 >>> importpickle2 >>>
3 >>> var_a = {'a':'str', 'c': True, 'e': 10, 'b': 11.1, 'd': None, 'f': [1, 2, 3], 'g':(4, 5, 6)}4
5 #序列化
6 >>> var_b =pickle.dumps(var_a)7 >>>var_b8 b'\x80\x03}q\x00(X\x01\x00\x00\x00eq\x01K\nX\x01\x00\x00\x00aq\x02X\x03\x00\x00\x00strq\x03X\x01\x00\x00\x00fq\x04]q\x05(K\x01K\x02K\x03eX\x01\x00\x00\x00gq\x06K\x04K\x05K\x06\x87q\x07X\x01\x00\x00\x00bq\x08G@&333333X\x01\x00\x00\x00cq\t\x88X\x01\x00\x00\x00dq\nNu.'
9
10 #反序列化
11 >>> var_c =pickle.loads(var_b)12 >>>var_c13 {'e': 10, 'a': 'str', 'f': [1, 2, 3], 'g': (4, 5, 6), 'b': 11.1, 'c': True, 'd': None}
View Code
dump()與load()
1 >>> importpickle2 >>>
3 >>> var_a = {'a':'str', 'c': True, 'e': 10, 'b': 11.1, 'd': None, 'f': [1, 2, 3], 'g':(4, 5, 6)}4
5 #持久化到文件
6 >>> with open('pickle.txt', 'wb') as f:7 ... pickle.dump(var_a, f)8 ...9
10 #從文件中讀取數據
11 >>> with open('pickle.txt', 'rb') as f:12 ... var_b =pickle.load(f)13 ...14 >>>var_b15 {'e': 10, 'a': 'str', 'f': [1, 2, 3], 'g': (4, 5, 6), 'b': 11.1, 'c': True, 'd': None}16 >>>
View Code
說明:
默認情況下Python 2.x中pickled后的數據是字符串形式,需要將它轉換為字節對象才能被Python 3.x中的pickle.loads()反序列化;Python 3.x中pickling所使用的協議是v3,因此需要在調用pickle.dumps()時指定可選參數protocol為Python 2.x所支持的協議版本(0,1,2),否則pickled后的數據不能被被Python 2.x中的pickle.loads()反序列化;
Python 3.x中pickle.dump()和pickle.load()方法中指定的文件對象,必須以二進制模式打開,而Python 2.x中可以以二進制模式打開,也可以以文本模式打開
pickle模塊可以直接對自定數據類型進行序列化/反序列化操作,無需編寫額外的處理函數或類。
1 >>> stu = Student('Tom', 19, 1)2 >>> print(stu)3 Student [name: Tom, age: 19, sno: 1]4
5 #序列化
6 >>> var_b =pickle.dumps(stu)7 >>>var_b8 b'\x80\x03c__main__\nStudent\nq\x00)\x81q\x01}q\x02(X\x04\x00\x00\x00nameq\x03X\x03\x00\x00\x00Tomq\x04X\x03\x00\x00\x00ageq\x05K\x13X\x03\x00\x00\x00snoq\x06K\x01ub.'
9
10 #反序列化
11 >>> var_c =pickle.loads(var_b)12 >>>var_c13 Student [name: Tom, age: 19, sno: 1]14
15 #持久化到文件
16 >>> with open('pickle.txt', 'wb') as f:17 ... pickle.dump(stu, f)18 ...19
20 #從文件總讀取數據
21 >>> with open('pickle.txt', 'rb') as f:22 ... pickle.load(f)23 ...24 Student [name: Tom, age: 19, sno: 1]
View Code
六:shelve模塊
shelve是一個簡單的數據存儲方案,類似key-value數據庫,可以很方便的保存python對象,其內部是通過pickle協議來實現數據序列化。shelve只有一個open()函數,這個函數用于打開指定的文件(一個持久的字典),然后返回一個shelf對象。shelf是一種持久的、類似字典的對象。它與“dbm”的不同之處在于,其values值可以是任意基本Python對象--pickle模塊可以處理的任何數據。這包括大多數類實例、遞歸數據類型和包含很多共享子對象的對象。keys還是普通的字符串。
open(filename, flag='c', protocol=None, writeback=False)
flag?參數表示打開數據存儲文件的格式,可取值與dbm.open()函數一致:
值描述
'r'
以只讀模式打開一個已經存在的數據存儲文件
'w'
以讀寫模式打開一個已經存在的數據存儲文件
'c'
以讀寫模式打開一個數據存儲文件,如果不存在則創建
'n'
總是創建一個新的、空數據存儲文件,并以讀寫模式打開
protocol?參數表示序列化數據所使用的協議版本,默認是pickle v3;
writeback?參數表示是否開啟回寫功能。
我們可以把shelf對象當dict來使用--存儲、更改、查詢某個key對應的數據,當操作完成之后,調用shelf對象的close()函數即可。當然,也可以使用上下文管理器(with語句),避免每次都要手動調用close()方法。
實例:內置數據類型操作
1 #保存數據
2 with shelve.open('student') as db:3 db['name'] = 'Tom'
4 db['age'] = 19
5 db['hobby'] = ['籃球', '看電影', '彈吉他']6 db['other_info'] = {'sno': 1, 'addr': 'xxxx'}7
8 #讀取數據
9 with shelve.open('student') as db:10 for key,value indb.items():11 print(key, ':', value)
View Code
輸出結果:
1 name : Tom2 age : 19
3 hobby : ['籃球', '看電影', '彈吉他']4 other_info : {'sno': 1, 'addr': 'xxxx'}
View Code
實例:自定義數據類型操作
1 #自定義class
2 classStudent(object):3 def __init__(self, name, age, sno):4 self.name =name5 self.age =age6 self.sno =sno7
8 def __repr__(self):9 return 'Student [name: %s, age: %d, sno: %d]' %(self.name, self.age, self.sno)10
11 #保存數據
12 tom = Student('Tom', 19, 1)13 jerry = Student('Jerry', 17, 2)14
15 with shelve.open("stu.db") as db:16 db['Tom'] =tom17 db['Jerry'] =jerry18
19 #讀取數據
20 with shelve.open("stu.db") as db:21 print(db['Tom'])22 print(db['Jerry'])23
24
25 輸出結果:26
27 Student [name: Tom, age: 19, sno: 1]28 Student [name: Jerry, age: 17, sno: 2]
View Code
七:總結
1. 對比
json模塊常用于編寫web接口,將Python數據轉換為通用的json格式傳遞給其它系統或客戶端;也可以用于將Python數據保存到本地文件中,缺點是明文保存,保密性差。另外,如果需要保存非內置數據類型需要編寫額外的轉換函數或自定義類。
pickle模塊和shelve模塊由于使用其特有的序列化協議,其序列化之后的數據只能被Python識別,因此只能用于Python系統內部。另外,Python 2.x 和 Python
3.x 默認使用的序列化協議也不同,如果需要互相兼容需要在序列化時通過protocol參數指定協議版本。除了上面這些缺點外,pickle模塊和shelve模塊相對于json模塊的優點在于對于自定義數據類型可以直接序列化和反序列化,不需要編寫額外的轉換函數或類。
shelve模塊可以看做是pickle模塊的升級版,因為shelve使用的就是pickle的序列化協議,但是shelve比pickle提供的操作方式更加簡單、方便。shelve模塊相對于其它兩個模塊在將Python數據持久化到本地磁盤時有一個很明顯的優點就是,它允許我們可以像操作dict一樣操作被序列化的數據,而不必一次性的保存或讀取所有數據。
2. 建議
需要與外部系統交互時用json模塊;
需要將少量、簡單Python數據持久化到本地磁盤文件時可以考慮用pickle模塊;
需要將大量Python數據持久化到本地磁盤文件或需要一些簡單的類似數據庫的增刪改查功能時,可以考慮用shelve模塊。
3. 附錄
要實現的功能可以使用的api
將Python數據類型轉換為(json)字符串
json.dumps()
將json字符串轉換為Python數據類型
json.loads()
將Python數據類型以json形式保存到本地磁盤
json.dump()
將本地磁盤文件中的json數據轉換為Python數據類型
json.load()
將Python數據類型轉換為Python特定的二進制格式
pickle.dumps()
將Python特定的的二進制格式數據轉換為Python數據類型
pickle.loads()
將Python數據類型以Python特定的二進制格式保存到本地磁盤
pickle.dump()
將本地磁盤文件中的Python特定的二進制格式數據轉換為Python數據類型
pickle.load()
以類型dict的形式將Python數據類型保存到本地磁盤或讀取本地磁盤數據并轉換為數據類型
shelve.open()
總結
以上是生活随笔為你收集整理的python建立数据库并序列化_Python之数据序列化(json、pickle、shelve)的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 优盘启动盘怎么用 如何制作优盘启动盘
- 下一篇: u盘格式化不了怎么办说有保护 U盘受保护