代码之家  ›  专栏  ›  技术社区  ›  Pj-

搁置模块不适用于“with”语句

  •  2
  • Pj-  · 技术社区  · 7 年前

    我试图在python中使用shelve模块,并试图将其与“with”语句相结合,但在尝试这样做时,我得到了以下错误:

    with shelve.open('shelve', 'c') as shlv_file:
        shlv_file['title']    = 'The main title of my app'
        shlv_file['datatype'] = 'data type int32'
        shlv_file['content']  = 'Lorem ipsum'
        shlv_file['refs']     = '<htppsa: asda.com>'
    
    print(shlv_file)
    

     with shelve.open('shelve', 'c') as shlv_file:
    AttributeError: DbfilenameShelf instance has no attribute '__exit__'
    

    尽管这样做:

    shlv_file = shelve.open('data/shelve', 'c')
    shlv_file['title']    = 'The main title of my app'
    shlv_file['datatype'] = 'data type int32'
    shlv_file['content']  = 'Lorem ipsum'
    shlv_file['refs']     = '<htppsa: asda.com>'
    shlv_file.close()
    
    shlv_file = shelve.open('data/shelve', 'c')
    shlv_file['new_filed'] = 'bla bla bla'
    print(shlv_file)
    

    没有出现错误,输出是预期的。第一个语法有什么问题?我在看一门python课程,在这门课程中,老师毫无问题地使用了第一个版本。

    1 回复  |  直到 7 年前
        1
  •  4
  •   cs95 abhishek58g    7 年前

    with 用于。它基本上用于自动处理它所调用的对象的设置和清理,前提是 . 特别是,设置的对象是 __enter__ __exit__

    In [355]: class Foo():
         ...:     def __enter__(self):
         ...:         print("Start!")
         ...:         return self
         ...:     def __exit__(self, type, value, traceback):
         ...:         print("End!")
         ...:         
    

    现在实例化 Foo 具有 with...as

    In [356]: with Foo() as x:
         ...:     print(x)
         ...:     
    Start!
    <__main__.Foo object at 0x1097f5da0>
    End!
    

    如你所见, 具有像 将强制调用这些设置/拆卸方法,如果缺少,则 AttributeError 将引发,因为尝试调用不存在的实例方法。

    这和你的 shelve 对象-它没有 __退出__ 方法在其类中定义,因此使用 不起作用。


    根据 documentation ,对上下文管理器的支持从版本3.4及以后添加。如果上下文管理器不工作,则意味着您的版本较旧。