• Python中的序列化以及pickle和json模块介绍


    Python中的序列化指的是在程序运行期间,变量都是在内存中保存着的,如果我们想保留一些运行中的变量值,就可以使用序列化操作把变量内容从内存保存到磁盘中,在Python中这个操作叫pickling,等下次再使用保存的变量时,可以通过反序列化操作提取数据内容到内存,即unpickling

    我们先来介绍pickle模块,它就是Python提供用来序列化对象的模块,假如现在我们把一个对象序列化。

    import pickle
    d=dict(name='zhangkang',age=20,sex='man')
    #以二进制的方式写入pk.txt
    with open('pk.txt','wb') as f:
        pickle.dump(d,f)

    这样在当前程序运行目录就会生成一个pk.txt文件,里面保存着d对象,下面我们把序列化的对象内容提取出来,也就是反序列化。

    import pickle
    with open('pk.txt','r') as f:
        d=pickle.load(f)
    print(type(d))
    print(d)
    
    输出:
    <type 'dict'>
    {'age': 20, 'name': 'zhangkang', 'sex': 'man'}

    **pickle.dump()直接把对象序列化后写入一个file-like Object:
    pickle.load()方法从一个file-like Object中直接反序列化出对象**

    当然我们也可以使用pickle.dumps()方法把对象序列化成一个str,然后,就可以把这个str写入文件。当我们要把对象从磁盘读到内存时,可以先把内容读到一个str,然后用pickle.loads()方法反序列化出对象

    import pickle
    d=dict(name='zhangkang',age=20,sex='man')
    s=pickle.dumps(d)
    #先看下s的类型和内容
    print(type(s))
    print(s)
    
    print('
    ')
    #把s保存到文件,再从文件读取,就是文件
    #操作的内容了,本程序不演示了,现在我们把s
    #反序列化
    ss=pickle.loads(s)
    print(type(ss))
    print(ss)
    
    输出:
    <type 'str'>
    (dp0
    S'age'
    p1
    I20
    sS'name'
    p2
    S'zhangkang'
    p3
    sS'sex'
    p4
    S'man'
    p5
    s.
    
    
    <type 'dict'>
    {'age': 20, 'name': 'zhangkang', 'sex': 'man'}

    json模块
    假如我们需要在不同的编程语言之间传递对象,就需要把对象序列化成标准格式,类型于XML,但是序列化成json比XML更好,速度也更快,并且可以直接在web页面读取,序列成json后其实就是个字符串,任何语言都能读取,也可以方便的存储到磁盘或者通过网络传输。

    JSON表示的对象就是标准的JavaScript语言的对象,JSON和Python内置的数据类型对应如下:
    json类型——Python类型
    { }——dict
    [ ]——,list
    string——str或者u’unicode’
    true/false——True/False
    null ——None

    Python内置的json模块提供了完善的Python对象到json格式的转换。先看看如何把Python对象变成一个json:

    import json
    d=dict(name='zhangkang',age=20,score=88)
    #这里dumps(),loads(),dump(),load()的用法和pickle模块一样
    a=json.dumps(d)
    print(type(a))
    #这里输出的字符串和上面讲的pickle的不同,格式变了。
    print(a)
    print('
    ')
    
    c=json.loads(a)
    print(type(c))
    #这里注意,所有反序列化后的字符串对象类型不是str,而是unicode,因为
    #JSON标准规定JSON编码是UTF-8,所以我们总能在Python的str或unicode与JSON的字符串之间转换。
    print(c)
    
    输出:
    <type 'str'>
    {"age": 20, "score": 88, "name": "zhangkang"}
    
    
    <type 'dict'>
    {u'age': 20, u'score': 88, u'name': u'zhangkang'}

    如果我们要对一个类对象序列化成标准格式:

    import json
    
    class People(object):
        def __init__(self,name,age,sex):
            self.name=name
            self.age=age
            self.sex=sex
    def people_dict(p):
        d=dict()
        d['name']=p.name
        d['age']=p.age
        d['sex']=p.sex
        return d
    p=People('zhangkang',24,'man')
    js_p=json.dumps(p,default=people_dict)
    print(type(js_p))
    print(js_p)
    
    输出:
    <type 'str'>
    {"age": 24, "name": "zhangkang", "sex": "man"}

    默认情况下,dumps()方法不知道如何将People()实例变为一个json的{ }对象。可选参数default就是把任意一个对象变成一个可序列为json的对象,我们只需要为People专门写一个转换函数,再把函数传进去。People()实例首先被people_dict()函数转换成dict,然后再被顺利序列化为json。

    如何把类对象反序列化呢?

    import json
    
    class People(object):
        def __init__(self,name,age,sex):
            self.name=name
            self.age=age
            self.sex=sex
    def people_dict(p):
        d=dict()
        d['name']=p.name
        d['age']=p.age
        d['sex']=p.sex
        return d
    def dict_people(d):
        return People(d['name'],d['age'],d['sex'])
    
    #序列化
    p=People('zhangkang',24,'man')
    js_p=json.dumps(p,default=people_dict)
    print(type(js_p))
    print(js_p)
    
    print('
    ')
    
    #反序列化
    pp=json.loads(js_p, object_hook=dict_people)
    print(type(pp))
    print(pp.name)
    print(pp.age)
    print(pp.sex)
    
    输出:
    <type 'str'>
    {"age": 24, "name": "zhangkang", "sex": "man"}
    
    
    <class '__main__.People'>
    zhangkang
    24
    man

    我们要把json反序列化为一个People对象实例,loads()方法首先把js_p转换成一个dict对象,然后把这个dict传入object_hook函数被转换为People实例。

  • 相关阅读:
    min-height IE6的解决方案
    javascript数据类型检测方法
    typeof、instanceof与isPrototypeOf()的差异与联系
    获取真实IP地址
    表格中的IE BUG
    【译】你对position的了解有多少?
    vim快捷键
    syntaxerror : unexpected token &
    .Net 高效开发之不可错过的实用工具
    @media screen 针对不同移动设备——响应式设计
  • 原文地址:https://www.cnblogs.com/neuzk/p/9476430.html
Copyright © 2020-2023  润新知