Chinaunix首页 | 论坛 | 博客
  • 博客访问: 167361
  • 博文数量: 31
  • 博客积分: 0
  • 博客等级: 民兵
  • 技术积分: 425
  • 用 户 组: 普通用户
  • 注册时间: 2014-10-13 17:05
文章分类

全部博文(31)

文章存档

2016年(11)

2015年(20)

我的朋友

分类: LINUX

2016-01-19 14:42:49

如果只需要存储一个简单的数据,shelve模块可以满足。
所要做的就是为它提供文件名。shelve最重要的函数是open,在调用它的时候(使用文件名作为参数),它会返回一个shelf对象,可以用它来存储内容。
只需要把它当成普通的字典就好。但是键一定要字符串,在完成工作之后,调用它的close方法。
1、潜在陷阱:
    意识到shelve.open函数返回的对象并不是普通的映射是很重要的,如下所示:
   
  1. In [2]: s = shelve.open('test.db')

  2. In [3]: s['x'] = ['a','b','c']

  3. In [4]: s['x']
  4. Out[4]: ['a', 'b', 'c']

  5. In [5]: s['x'].append('d')

  6. In [6]: s['x']
  7. Out[6]: ['a', 'b', 'c']
(1)列表['a', 'b', 'c']存储在键x下
(2)获得存储的表示,并且根据它来创建新的列表,而'd'被添加到这个副本中,修改的版本还没有被保存。
(3)最终,再次获得原始版本——没有'd'

为了避免上面的问题,在使用shelve模块修改存储的对象,必须将临时变量绑定到获得的副本上,并且在它被修改后重新存储这个副本。

  1. In [1]: import shelve

  2. In [2]: s = shelve.open('test.db')

  3. In [3]: s['x'] = ['a','b','c']

  4. In [4]: s['x']
  5. Out[4]: ['a', 'b', 'c']

  6. In [5]: temp = s['x']        # 将副本绑定到临时变量上。

  7. In [6]: temp.append('d')

  8. In [7]: s['x'] = temp        # 再将临时变量写到副本上。

  9. In [8]: s['x']
  10. Out[8]: ['a', 'b', 'c', 'd']
2.简单的数据示例:

  1. #!/usr/bin/python
  2. import shelve
  3. def store_person(db):    # 创建数据
  4.     pid = raw_input('Enter unique ID number: ')     # 键值
  5.     person = {}    # 定义person为字典
  6.     person['name'] = raw_input('Enter name: ')    # 在person里定义子字典
  7.     person['age'] = raw_input('Enter age: ')
  8.     person['phone'] = raw_input('Enter phone: ')
  9.     db[pid] = person    # 完成键值对应关系,保存到数据库
  10. def lookup_person(db):
  11.     pid = raw_input('Enter ID numbers: ')    # 获取键
  12.     field = raw_input('What would you like to know ?(name,age,phone)')    # 获取子字典的键
  13.     print field.capitalize() + ":",db[pid][field]    
  14. def print_help():
  15.     print 'The available commands are:'
  16.     print 'store : stores information about a person'
  17.     print 'lookup : looks up a person from ID number'
  18.     print 'quit : save changes and exit'
  19.     print '? : prints this message'
  20. def enter_command():
  21.     cmd = raw_input('Enter command(? for help): ')
  22.     cmd = cmd.strip().lower()
  23.     return cmd
  24. def main():
  25.     database = shelve.open('test.db')    # 创建shelve数据库
  26.     try:
  27.     while True:
  28.      cmd = enter_command()
  29.      if cmd == 'store':
  30.         store_person(database)
  31.      elif cmd == 'lookup':
  32.         lookup_person(database)
  33.      elif cmd == '?':
  34.         print_help()
  35.      elif cmd == 'quit':
  36.         return
  37.     finally:
  38.     database.close()

  39. if __name__ == '__main__':main()
(1)以上代码将所有内容都放到函数中会让程序更加结构化。
(2)主程序放到main函数中,只有在if __name__ == '__main__'条件成立的时候才被调用。这意味着可以在其他程序中将这个程序作为模块导入,然后调用main()函数。
(3)在main函数中打开数据库,然后将其作为参数传给另外需要它的函数。在大多数情况下最好避免使用全局变量。
(4)对读取的内容调用strip和lower函数以生成了一个修改后的版本。如果总是对用户的输入使用strip和lower函数,那么就可以让用户随意输入大小写字母和添加空格
(5)使用try/finally确保数据库能正常关闭。我们永远不知道什么时候会出错,如果程序在没有正确关闭数据库的情况下终止,那么数据库文件就有可能被损坏。

运行结果如下:

  1. [root@server1 python]# ./database1.py
  2. Enter command(? for help): ?
  3. The available commands are:
  4. store : stores information about a person
  5. lookup : looks up a person from ID number
  6. quit : save changes and exit
  7. ? : prints this message
  8. Enter command(? for help): store
  9. Enter unique ID number: 002
  10. Enter name: xixi
  11. Enter age: 20
  12. Enter phone: 133
  13. Enter command(? for help): lookup
  14. Enter ID numbers: 002
  15. What would you like to know ?(name,age,phone)name
  16. Name: xixi
  17. Enter command(? for help): lookup
  18. Enter ID numbers: 002
  19. What would you like to know ?(name,age,phone)age
  20. Age: 20
  21. Enter command(? for help): quit
虽然普通字典也能达到这样的效果,但是shelve是将数据字典存储在数据库文件中,是存储在磁盘上,只要数据库文件不损坏,数据也不会丢失。
阅读(3734) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~