2009-08-25 25 views
2

シェルフモジュールを使用すると、私には驚くべき動作がいくつかあります。 keys()、iter()、およびiteritems()は、棚のすべてのエントリを返しません!ここでは、コードです:シェルフモジュールに問題がありますか?

cache = shelve.open('my.cache') 
# ... 
cache[url] = (datetime.datetime.today(), value) 

以降:

cache = shelve.open('my.cache') 
urls = ['accounts_with_transactions.xml', 'targets.xml', 'profile.xml'] 
try: 
    print list(cache.keys()) # doesn't return all the keys! 
    print [url for url in urls if cache.has_key(url)] 
    print list(cache.keys()) 
finally: 
    cache.close() 

、ここでは出力です:

['targets.xml'] 
['accounts_with_transactions.xml', 'targets.xml'] 
['targets.xml', 'accounts_with_transactions.xml'] 

は、誰もがこの前に実行され、そしてこの問題を回避するには、すべての可能なキャッシュキーを知らなくても、そこにあります先行技術0002

+0

どのdbmモジュールを使用していますか?私のバグのように聞こえる。 –

+0

whichdb.whichdb( 'my.cache')=> dbm –

+0

(btw、これはMacの場合はPython 2.5です) –

答えて

3

のために何を得るのです。それが使用されている場合

...データベースは、また、DBMの制限のために(残念ながら)主題である - これはつまり、(

import shelve 

a = 'trxns.xml' 
b = 'foobar.xml' 
c = 'profile.xml' 

urls = [a, b, c] 
cache = shelve.open('my.cache', 'c') 

try: 
    cache[a] = a*1000 
    cache[b] = b*10000 
finally: 
    cache.close() 


cache = shelve.open('my.cache', 'c') 

try: 
    print cache.keys() 
    print [url for url in urls if cache.has_key(url)] 
    print cache.keys() 
finally: 
    cache.close() 
:データベースに格納されたオブジェクト)の漬け表現は、これは正しく「バグ」を再現し

...かなり小さくする必要があります出力と

[] 
['trxns.xml', 'foobar.xml'] 
['foobar.xml', 'trxns.xml'] 

答えは、それゆえ、大のようなものの生のXML-ではなく、棚での計算の結果を格納していないです。

+0

Python 2.6ではこの「バグ」を再現できません。 – NicDumZ

+0

dbmを使用していない可能性があります。whichdb.whichdb( 'my.cache')を試してください。私のMacでは、それは 'dbm'を生成します。まだ他のシステムでは試していません。 –

0

あなたの例を見て、私の最初の考えは、cache.has_key()に副作用があることです。つまり、この呼び出しはキャッシュにキーを追加します。あなたはpython library referenceによる

print cache.has_key('xxx') 
print list(cache.keys()) 
+0

質問コードをURLの短縮バージョンで更新しました –

+0

まだ計算されません。単一のURLをキャッシュに追加しますが、 'has_key'の後には、キャッシュに2つのURLがあります。副作用があるはずです。 –

+0

キャッシュに実際には2つのURLがあります。 keys()は私が明示的にそれぞれをテストするまでそれらを両方表示しません。 –