python之shelve模块详解2(转)

Posted suoha2018

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了python之shelve模块详解2(转)相关的知识,希望对你有一定的参考价值。

一、定义

Shelve是对象持久化保存方法,将对象保存到文件里面,缺省(即默认)的数据存储文件是二进制的。

二、用途

可以作为一个简单的数据存储方案。

三、用法

使用时,只需要使用open函数获取一个shelf对象,然后对数据进行增删改查操作,在完成工作、并且将内存存储到磁盘中,最后调用close函数变回将数据写入文件。

四、关联模块Anydbm

相同点:
1.anydbm, shelve 都是对象持久化保存方法,将对象保存到文件里面,缺省的数据存储文件是二进制的。这两个模块允许我们将一个磁盘上的文件与一个”dict-like”对象(类字典对象)关联起来,操作这个“dict-like”对象,就像操作dict对象一项,最后可以将“dict-like”的数据持久化到文件。
2.都可以使用open函数。

区别:
anydbm的key和value的类型必须都是字符串,而shelve的key要求必须是字符串,value则可以是任意合法的python数据类型。

五、方法

1.shelve.open(filename, flag=’c’, protocol=None, writeback=False):创建或打开一个shelve对象。shelve默认打开方式支持同时读写操作。
filename是关联的文件路径。
可选参数flag,默认为‘c’,如果数据文件不存在,就创建,允许读写;可以是: ‘r’: 只读;’w’: 可读写; ‘n’: 每次调用open()都重新创建一个空的文件,可读写。
protocol:是序列化模式,默认值为None。具体还没有尝试过,从pickle的资料中查到以下信息【protocol的值可以是1或2,表示以二进制的形式序列化】

2.shelve.close()
同步并关闭shelve对象。
注意:每次使用完毕,都必须确保shelve对象被安全关闭。同样可以使用with语句
with shelve.open(spam) as db:
    db[eggs] = eggs

六、writeback参数

writeback:默认为False。当设置为True以后,shelf将会将所有从DB中读取的对象存放到一个内存缓存。当我们close()打开的shelf的时候,缓存中所有的对象会被重新写入DB。
writeback方式有优点也有缺点。
优点是减少了我们出错的概率,并且让对象的持久化对用户更加的透明了;但这种方式并不是所有的情况下都需要,首先,使用writeback以后,shelf在open()的时候会增加额外的内存消耗,并且当DB在close()的时候会将缓存中的每一个对象都写入到DB,这也会带来额外的等待时间。因为shelve没有办法知道缓存中哪些对象修改了,哪些对象没有修改,因此所有的对象都会被写入。

注意:为了保存增、删、改的内容,建议显示的标明writeback=True。
技术分享图片

# 七、代码示例
# 1.创建一个shelf对象,直接使用open函数即可

import shelve
s = shelve.open(test_shelf.db)         #
try:
    s[kk] = {int: 10, float: 9.5, String: Sample data}
    s[MM] = [1, 2, 3]
finally:
    s.close()

# 2.如果想要再次访问这个shelf,只需要再次shelve.open()就可以了,然后我们可以像使用字典一样来使用这个shelf

import shelve
try:
    s = shelve.open(test_shelf.db)
    value = s[kk]
    print(value)
finally:
    s.close()

# 3.对shelf对象,增、删、改操作

import shelve
s = shelve.open(test_shelf.db, flag=w, writeback=True)
try:
    # 增加
    s[QQQ] = 2333
    # 删除
    del s[MM]
    # 修改
    s[kk] = {String: day day up}
finally:
    s.close()

# 注意:flag设置为‘r’-只读模式,当程序试图去修改一个以只读方式打开的DB时,将会抛一个访问错误的异常。异常的具体类型取决于anydbm这个模块在创建DB时所选用的DB。异常举例:anydbm.error: need ‘c’ or ‘n’ flag to open new db

# 4.循环遍历shelf对象

import shelve
s = shelve.open(test_shelf.db)
try:
    # 方法一:
    for item in s.items():
        print (键[{}] = 值[{}].format(item[0], s[item[0]]))
    # 方法二:
    for key, value in s.items():
        print(key, value)
finally:
    s.close()

# 5.备注一个错误:
# open中的参数filename,起初认为需要手动新建一个.db,或者.dat的文件,目前电脑中无任何真正的数据库文件,所以采用了新建txt文件,修改后缀的方法创建.db,或者.dat的文件。
# 解释器报错,提示内容为:"anydbm.error: db type could not be determined",
# 原因是是filename已经存在,并且格式与shelve不符,所以提示 “db type could not be determined”。
# 解决方法是,删除该文件。首次运行后会自动生成该filename文件。
# 6.稍微复杂些的案例,实现一个简单提问式的数据库

# encoding:utf-8
# 2018/3/8

# 简单的数据库

import sys,shelve

def print_help():
    存储(增加)、查找、更新(修改)、循环打印、删除、退出、帮助
    print(The available commons are: )
    print(store    : Stores information about a person)
    print(lookup   : Looks up a person from ID numbers)
    print("update   : Update a person‘s information from ID number")
    print(print_all: Print all informations)
    print("delete   : Delete a person‘s information from ID number")
    print(quit     : Save changes and exit)
    print(?        : Print this message)


def store_people(db):
    pid = input(Please enter a unique ID number: )
    person = {}
    person[name] = input(Please enter the name: )
    person[age] = input(Please enter the age: )
    person[phone] = input(Please enter the phone: )
    db[pid] = person
    print("Store information: pid is %s, information is %s" % (pid, person))


def lookup_people(db):
    pid = input(Please enter the number: )
    field = input(What would you like to know? (name, age, phone) )
    if pid in db.keys():
        value = db[pid][field]
        print("Pid %s‘s %s is %s" % (pid, field, value))
    else:
        print(Not found this number)


def update_people(db):
    pid = input(Please enter the number: )
    field = input(What would you like to update? (name, age, phone)  )
    newvalue = input(Enter the new information: )
    if pid in db.keys():
        value = db[pid]
        value[field] = newvalue
        print("Pid %s‘s %s update information is %s" % (pid, field, newvalue))
    else:
        print("Not found this number, can‘t update")


def delete_people(db):
    pid = input(Please enter the number: )
    if pid in db.keys():
        del db[pid]
        print("pid %s‘s information delete done" % pid)
    else:
        print( "Not found this number, can‘t delete")

def print_all_people(db):
    print( All information are: )
    for key, value in db.items():
        print(key, value)

def enter_cmd():
    cmd = input(Please enter the cmd(? for help): )
    cmd = cmd.strip().lower()
    return cmd

def main():
    database = shelve.open(database201803.dat, writeback=True)
    try:
        while True:
            cmd = enter_cmd()
            if cmd == store:
                store_people(database)
            elif cmd == lookup:
                lookup_people(database)
            elif cmd == update:
                update_people(database)
            elif cmd == print_all:
                print_all_people(database)
            elif cmd == delete:
                delete_people(database)
            elif cmd == ?:
                print_help()
            elif cmd == quit:
                return
    finally:
        database.close()

if __name__ == __main__:
    main()

技术分享图片
技术分享图片
# shelve模块比pickle模块简单,只有一个open函数,返回类似字典的对象,可读可写;
# key必须为字符串,而值可以是python所支持的数据类型
# shelve模块(**)------可以当做数据库用,以后基本不会用,(可以很方面的往文件中写数据类型和读)
import shelve             #存取很方便(可以做一个简单的数据存储方案)
f=shelve.open(rsheve.txt)
f[stu1_info]={name:egon,age:18,hobby:[piao,smoking,drinking]}   #
f[stu2_info]={name:gangdan,age:53}
f[school_info]={website:http://www.pypy.org,city:beijing}
print(f[stu1_info][hobby])
f.close()
 
import shelve
d=shelve.open(ra.txt)                   #生成三个文件分别是:a.txt.baka.txt.data.txt.dir
d[tom]={age:18,sex:male}         #存的时候会生成三个文件,不用管,是python的一种处理机制
print(d[tom][sex])                   #可以取出字典中的key对应的value
print(d[tom])                          #取出tom对应的字典
d.close()

import shelve
d=shelve.open(ra.txt,writeback=True)    #writeback=True,对子字典修改完后要写回,否则不会看到修改后的结果
d[egon]={age:18,sex:male}         #存的时候会生成三个文件,不用管,是python的一种处理机制
d[egon][age]=20                       #将年龄修改为20
print(d[egon][age])                   #此时拿到的是修改后的年龄
print(d[egon][sex])
d.close()
技术分享图片

 

文章出处:https://www.cnblogs.com/sui776265233/p/9225164.html


















以上是关于python之shelve模块详解2(转)的主要内容,如果未能解决你的问题,请参考以下文章

python 模块之-shelve

python 之 random 模块 shutil 模块shelve模块 xml模块

Python之常用模块

python序列化_json,pickle,shelve模块

Python基础(12)_python模块之sys模块logging模块序列化json模块pickle模块shelve模块

Python之数据序列化(jsonpickleshelve)