简体   繁体   中英

The python shelve.open(…,flag='n') does not create an empty shelve

I am using the Python shelve module and the following python version: Python 3.3.0 (v3.3.0:bd8afb90ebf2, Sep 29 2012, 10:55:48) [MSC v.1600 32 bit (Intel)] on win32 . The flag parameter of the shelve.open method is described here :

The optional flag parameter has the same interpretation as the flag parameter of dbm.open().

and the dbm flag parameter is described here :

'n' Always create a new, empty database, open for reading and writing

But the following program did not work as I expected:

import shelve
import os
import os.path
import shutil
myshelvedir='C:\\testdir'
myshelvefile=os.path.join(myshelvedir,'myshelve')
os.mkdir(myshelvedir)
try:
    myshelve=shelve.open(myshelvefile)
    try:
        myshelve['key1']='value1'
        print(1,dict(myshelve))
    finally:
        myshelve.close()

    myshelve=shelve.open(myshelvefile,'n')
    try:
        myshelve['key2']='value2'
        print(2,dict(myshelve))
    finally:
        myshelve.close()

finally:
    shutil.rmtree(myshelvedir)

The output was

1 {'key1': 'value1'}
2 {'key1': 'value1', 'key2': 'value2'}

For the second line I expected

2 {'key2': 'value2'}

because the shelve was opened with the 'n' flag and therefore the database should be empty after opening.

Do I miss something?

Additional tests:

On

Python 3.0.1 (r301:69561, Feb 13 2009, 20:04:18) [MSC v.1500 32 bit (Intel)] on win32

I also get

2 {'key2': 'value2', 'key1': 'value1'}

On

Python 2.6.4 (r264:75706, Jun 27 2012, 05:45:50) [C] on sunos5

I get the expected

(2, {'key2': 'value2'})

Also on Python 2.7.5 (default, May 15 2013, 22:43:36) [MSC v.1500 32 bit (Intel)] on win 32

I get

(2, {'key2': 'value2'})

So this is a new feature or a bug in 3

I found http://bugs.python.org/issue18039 .

Title: dbm.open(..., flag="n") does not work and does not give a warning

which gives an explanation.

The documentation says that shelve uses one of the available database interfaces.

http://docs.python.org/3/library/shelve.html

12.3. shelve — Python object persistence
...
shelve. open (filename, flag='c', protocol=None, writeback=False)
Open a persistent dictionary.
...
The optional flag parameter has the same interpretation as the flag parameter of dbm.open().
...
12.3.1. Restrictions The choice of which database package will be used (such as dbm.ndbm or dbm.gnu) depends on which interface is available. Therefore it is not safe to open the database directly using dbm.

and that the 'n' flag works like in dbm.open

http://docs.python.org/3/library/dbm.html

12.5. dbm — Interfaces to Unix “databases”
dbm is a generic interface to variants of the DBM database — dbm.gnu or dbm.ndbm. If none of these modules is installed, the slow-but-simple implementation in module dbm.dumb will be used
...
'n' : Always create a new, empty database, open for reading and writing

But this definition of the n-flag contradicts to the definition of the n-flag if it falls back to dbms.dumb

http://docs.python.org/3/library/dbm.html#module-dbm.gnu

12.5.1. dbm.gnu — GNU's reinterpretation of dbm
Platforms: Unix

http://docs.python.org/3/library/dbm.html#module-dbm.dumb says

12.5.3. dbm.dumb — Portable DBM implementation
...
dbm.dumb.open(filename[, flag[, mode]]) ... The optional flag argument is currently ignored; the database is always opened for update, and will be created if it does not exist.

So this maybe not an issue on Unix implementations where gnu.dbm libraries are installed (I don't have access to a python 3 on Unix to test this)

From this I conclude that there some conflicting statements in the python documentation: On unix systems where dbm libraries are installed python shelve will use this dbm installation an here the 'n' flag works as described in the documentation.

If no dbm installation can be found (eg on windows systems) the dbm.dumb module will be used where the 'n' works like the 'c' flag.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM